diff --git a/sfntly/Android.mk b/sfntly/Android.mk
new file mode 100644
index 0000000..40e35d2
--- /dev/null
+++ b/sfntly/Android.mk
@@ -0,0 +1,238 @@
+BASE_PATH := $(call my-dir)
+LOCAL_PATH:= $(call my-dir)
+
+include $(CLEAR_VARS)
+LOCAL_ADDITIONAL_DEPENDENCIES := $(LOCAL_PATH)/Android.mk
+
+# We default to release for the Android build system. Developers debugging
+# code can build with "Debug"
+GYP_CONFIGURATION := Release
+
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_MODULE := libsfntly
+LOCAL_MODULE_SUFFIX := .a
+LOCAL_MODULE_TAGS := optional
+
+LOCAL_CPP_EXTENSION := .cc
+LOCAL_GENERATED_SOURCES :=
+
+LOCAL_SRC_FILES := \
+	cpp/src/sfntly/data/byte_array.cc \
+	cpp/src/sfntly/data/font_data.cc \
+	cpp/src/sfntly/data/font_input_stream.cc \
+	cpp/src/sfntly/data/font_output_stream.cc \
+	cpp/src/sfntly/data/growable_memory_byte_array.cc \
+	cpp/src/sfntly/data/memory_byte_array.cc \
+	cpp/src/sfntly/data/readable_font_data.cc \
+	cpp/src/sfntly/data/writable_font_data.cc \
+	cpp/src/sfntly/font.cc \
+	cpp/src/sfntly/font_factory.cc \
+	cpp/src/sfntly/port/file_input_stream.cc \
+	cpp/src/sfntly/port/lock.cc \
+	cpp/src/sfntly/port/memory_input_stream.cc \
+	cpp/src/sfntly/port/memory_output_stream.cc \
+	cpp/src/sfntly/table/bitmap/big_glyph_metrics.cc \
+	cpp/src/sfntly/table/bitmap/bitmap_glyph.cc \
+	cpp/src/sfntly/table/bitmap/bitmap_glyph_info.cc \
+	cpp/src/sfntly/table/bitmap/bitmap_size_table.cc \
+	cpp/src/sfntly/table/bitmap/composite_bitmap_glyph.cc \
+	cpp/src/sfntly/table/bitmap/ebdt_table.cc \
+	cpp/src/sfntly/table/bitmap/eblc_table.cc \
+	cpp/src/sfntly/table/bitmap/ebsc_table.cc \
+	cpp/src/sfntly/table/bitmap/glyph_metrics.cc \
+	cpp/src/sfntly/table/bitmap/index_sub_table.cc \
+	cpp/src/sfntly/table/bitmap/index_sub_table_format1.cc \
+	cpp/src/sfntly/table/bitmap/index_sub_table_format2.cc \
+	cpp/src/sfntly/table/bitmap/index_sub_table_format3.cc \
+	cpp/src/sfntly/table/bitmap/index_sub_table_format4.cc \
+	cpp/src/sfntly/table/bitmap/index_sub_table_format5.cc \
+	cpp/src/sfntly/table/bitmap/simple_bitmap_glyph.cc \
+	cpp/src/sfntly/table/bitmap/small_glyph_metrics.cc \
+	cpp/src/sfntly/table/byte_array_table_builder.cc \
+	cpp/src/sfntly/table/core/cmap_table.cc \
+	cpp/src/sfntly/table/core/font_header_table.cc \
+	cpp/src/sfntly/table/core/horizontal_device_metrics_table.cc \
+	cpp/src/sfntly/table/core/horizontal_header_table.cc \
+	cpp/src/sfntly/table/core/horizontal_metrics_table.cc \
+	cpp/src/sfntly/table/core/maximum_profile_table.cc \
+	cpp/src/sfntly/table/core/name_table.cc \
+	cpp/src/sfntly/table/core/os2_table.cc \
+	cpp/src/sfntly/table/font_data_table.cc \
+	cpp/src/sfntly/table/generic_table_builder.cc \
+	cpp/src/sfntly/table/header.cc \
+	cpp/src/sfntly/table/subtable.cc \
+	cpp/src/sfntly/table/table.cc \
+	cpp/src/sfntly/table/table_based_table_builder.cc \
+	cpp/src/sfntly/table/truetype/glyph_table.cc \
+	cpp/src/sfntly/table/truetype/loca_table.cc \
+	cpp/src/sfntly/tag.cc \
+	cpp/src/sample/chromium/font_subsetter.cc \
+	cpp/src/sample/chromium/subsetter_impl.cc
+
+
+# Flags passed to both C and C++ files.
+MY_CFLAGS_Debug := \
+	-fstack-protector \
+	--param=ssp-buffer-size=4 \
+	-Werror \
+	-fno-exceptions \
+	-fno-strict-aliasing \
+	-Wall \
+	-Wno-unused-parameter \
+	-Wno-missing-field-initializers \
+	-fvisibility=hidden \
+	-pipe \
+	-fPIC \
+	-fno-tree-sra \
+	-fuse-ld=gold \
+	-Wno-psabi \
+	-ffunction-sections \
+	-funwind-tables \
+	-g \
+	-fstack-protector \
+	-fno-short-enums \
+	-finline-limit=64 \
+	-Wa,--noexecstack \
+	-U_FORTIFY_SOURCE \
+	-Wno-extra \
+	-Wno-ignored-qualifiers \
+	-Wno-type-limits \
+	-Os \
+	-g \
+	-fomit-frame-pointer \
+	-fdata-sections \
+	-ffunction-sections
+
+MY_DEFS_Debug := \
+	'-DANGLE_DX11' \
+	'-D_FILE_OFFSET_BITS=64' \
+	'-DNO_TCMALLOC' \
+	'-DDISCARDABLE_MEMORY_ALWAYS_SUPPORTED_NATIVELY' \
+	'-DSYSTEM_NATIVELY_SIGNALS_MEMORY_PRESSURE' \
+	'-DDISABLE_NACL' \
+	'-DCHROMIUM_BUILD' \
+	'-DUSE_LIBJPEG_TURBO=1' \
+	'-DUSE_PROPRIETARY_CODECS' \
+	'-DENABLE_CONFIGURATION_POLICY' \
+	'-DENABLE_GPU=1' \
+	'-DUSE_OPENSSL=1' \
+	'-DENABLE_EGLIMAGE=1' \
+	'-DSFNTLY_NO_EXCEPTION' \
+	'-DU_USING_ICU_NAMESPACE=0' \
+	'-D__STDC_CONSTANT_MACROS' \
+	'-D__STDC_FORMAT_MACROS' \
+	'-DANDROID' \
+	'-D__GNU_SOURCE=1' \
+	'-DUSE_STLPORT=1' \
+	'-D_STLP_USE_PTR_SPECIALIZATIONS=1' \
+	'-DCHROME_BUILD_ID=""' \
+	'-DDYNAMIC_ANNOTATIONS_ENABLED=1' \
+	'-DWTF_USE_DYNAMIC_ANNOTATIONS=1' \
+	'-D_DEBUG'
+
+# Include paths placed before CFLAGS/CPPFLAGS
+LOCAL_C_INCLUDES_Debug := \
+	$(LOCAL_PATH)/cpp/src \
+	$(LOCAL_PATH) \
+	frameworks/wilhelm/include \
+
+
+# Flags passed to only C++ (and not C) files.
+LOCAL_CPPFLAGS_Debug := \
+	-fno-rtti \
+	-fno-threadsafe-statics \
+	-fvisibility-inlines-hidden \
+	-Wsign-compare \
+	-Wno-abi \
+	-Wno-error=c++0x-compat \
+	-Wno-non-virtual-dtor \
+	-Wno-sign-promo
+
+
+# Flags passed to both C and C++ files.
+MY_CFLAGS_Release := \
+	-fstack-protector \
+	--param=ssp-buffer-size=4 \
+	-Werror \
+	-fno-exceptions \
+	-fno-strict-aliasing \
+	-Wall \
+	-Wno-unused-parameter \
+	-Wno-missing-field-initializers \
+	-fvisibility=hidden \
+	-pipe \
+	-fPIC \
+	-fno-tree-sra \
+	-fuse-ld=gold \
+	-Wno-psabi \
+	-ffunction-sections \
+	-funwind-tables \
+	-g \
+	-fstack-protector \
+	-fno-short-enums \
+	-finline-limit=64 \
+	-Wa,--noexecstack \
+	-U_FORTIFY_SOURCE \
+	-Wno-extra \
+	-Wno-ignored-qualifiers \
+	-Wno-type-limits \
+	-Os \
+	-fno-ident \
+	-fdata-sections \
+	-ffunction-sections \
+	-fomit-frame-pointer
+
+MY_DEFS_Release := \
+	'-DANGLE_DX11' \
+	'-D_FILE_OFFSET_BITS=64' \
+	'-DNO_TCMALLOC' \
+	'-DDISCARDABLE_MEMORY_ALWAYS_SUPPORTED_NATIVELY' \
+	'-DSYSTEM_NATIVELY_SIGNALS_MEMORY_PRESSURE' \
+	'-DDISABLE_NACL' \
+	'-DCHROMIUM_BUILD' \
+	'-DUSE_LIBJPEG_TURBO=1' \
+	'-DUSE_PROPRIETARY_CODECS' \
+	'-DENABLE_CONFIGURATION_POLICY' \
+	'-DENABLE_GPU=1' \
+	'-DUSE_OPENSSL=1' \
+	'-DENABLE_EGLIMAGE=1' \
+	'-DSFNTLY_NO_EXCEPTION' \
+	'-DU_USING_ICU_NAMESPACE=0' \
+	'-D__STDC_CONSTANT_MACROS' \
+	'-D__STDC_FORMAT_MACROS' \
+	'-DANDROID' \
+	'-D__GNU_SOURCE=1' \
+	'-DUSE_STLPORT=1' \
+	'-D_STLP_USE_PTR_SPECIALIZATIONS=1' \
+	'-DCHROME_BUILD_ID=""' \
+	'-DNDEBUG' \
+	'-DNVALGRIND' \
+	'-DDYNAMIC_ANNOTATIONS_ENABLED=0' \
+	'-D_FORTIFY_SOURCE=2'
+
+
+# Include paths placed before CFLAGS/CPPFLAGS
+LOCAL_C_INCLUDES_Release := \
+	$(LOCAL_PATH)/cpp/src \
+	$(LOCAL_PATH) \
+	frameworks/wilhelm/include \
+
+
+# Flags passed to only C++ (and not C) files.
+LOCAL_CPPFLAGS_Release := \
+	-fno-rtti \
+	-fno-threadsafe-statics \
+	-fvisibility-inlines-hidden \
+	-Wsign-compare \
+	-Wno-abi \
+	-Wno-error=c++0x-compat \
+	-Wno-non-virtual-dtor \
+	-Wno-sign-promo
+
+LOCAL_SHARED_LIBRARIES := libicuuc libicui18n
+
+LOCAL_CFLAGS := $(MY_CFLAGS_$(GYP_CONFIGURATION)) $(MY_DEFS_$(GYP_CONFIGURATION))
+LOCAL_C_INCLUDES := $(LOCAL_C_INCLUDES_$(GYP_CONFIGURATION))
+LOCAL_CPPFLAGS := $(LOCAL_CPPFLAGS_$(GYP_CONFIGURATION))
+
+include $(BUILD_STATIC_LIBRARY)
diff --git a/sfntly/COPYING.android b/sfntly/COPYING.android
new file mode 100644
index 0000000..13bcce2
--- /dev/null
+++ b/sfntly/COPYING.android
@@ -0,0 +1,2 @@
+See cpp/COPYING for license details.
+
diff --git a/sfntly/CleanSpec.mk b/sfntly/CleanSpec.mk
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/sfntly/CleanSpec.mk
diff --git a/sfntly/MODULE_LICENSE_APACHE2 b/sfntly/MODULE_LICENSE_APACHE2
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/sfntly/MODULE_LICENSE_APACHE2
diff --git a/sfntly/README.android b/sfntly/README.android
new file mode 100644
index 0000000..e99dcf1
--- /dev/null
+++ b/sfntly/README.android
@@ -0,0 +1,2 @@
+Current version:
+svn checkout http://sfntly.googlecode.com/svn/trunk/cpp/src@134 cpp/src
diff --git a/sfntly/cpp/CMakeLists.txt b/sfntly/cpp/CMakeLists.txt
new file mode 100644
index 0000000..85932bc
--- /dev/null
+++ b/sfntly/cpp/CMakeLists.txt
@@ -0,0 +1,123 @@
+########################################################################
+# CMake build script for Google Typography sfntly.
+cmake_minimum_required(VERSION 2.6.2)
+set(CMAKE_CONFIGURATION_TYPES "Debug;Release" CACHE STRING "good configs" FORCE)
+set(CMAKE_LEGACY_CYGWIN_WIN32 0)
+
+project(sfntly)
+
+# For gcc, make the default be debug build and valgrind friendly.
+if(CMAKE_COMPILER_IS_GNUCXX)
+  if(NOT CMAKE_BUILD_TYPE)
+    set(CMAKE_BUILD_TYPE Debug)
+    add_definitions("-DDEBUG -D_DEBUG -g -fno-inline -fno-omit-frame-pointer -fno-builtin")
+  endif(NOT CMAKE_BUILD_TYPE)
+endif(CMAKE_COMPILER_IS_GNUCXX)
+
+  set(LIBRARY_OUTPUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/lib)
+  set(EXECUTABLE_OUTPUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/bin)
+  include_directories(${CMAKE_CURRENT_SOURCE_DIR}/src ext/gtest/include ext/gtest
+    ${CMAKE_CURRENT_SOURCE_DIR}/src/sample ${CMAKE_CURRENT_SOURCE_DIR}/src/sample/subtly)
+
+# The following simulates Chrome compilation flags
+  add_definitions(-DSFNTLY_NO_EXCEPTION)
+if(CMAKE_COMPILER_IS_GNUCXX)
+  add_definitions(-D__wur=__attribute__\(\(warn_unused_result\)\) -Wall -Werror -fno-exceptions)
+endif(CMAKE_COMPILER_IS_GNUCXX)
+
+# Use STL for TinyXML library
+  add_definitions(-DTIXML_USE_STL)
+
+# Enable CMap and Bitmap handling
+  add_definitions(-DSFNTLY_EXPERIMENTAL)
+
+# VC specific flags
+if(MSVC10 OR MSVC90)
+  set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /Zi /nologo /W4 /WX /O2 /Ob2 /Oy /GF /Gm- /MT /GS /Gy /fp:precise /Zc:wchar_t /Zc:forScope /GR-")
+  set (CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} /Zi /nologo /W4 /WX /Od /Oy- /RTC1 /MTd /GS /Gy /fp:precise /Zc:wchar_t /Zc:forScope /GR-")
+  add_definitions(-D_UNICODE -DUNICODE)
+  include_directories(${CMAKE_CURRENT_SOURCE_DIR}/ext/icu/include)
+  link_directories(${CMAKE_CURRENT_SOURCE_DIR}/ext/icu/lib)
+endif(MSVC10 OR MSVC90)
+
+  file(GLOB SFNTLY_CORE_FILES src/sfntly/*.h src/sfntly/*.cc)
+  file(GLOB SFNTLY_PORT_FILES src/sfntly/port/*.h src/sfntly/port/*.cc)
+  file(GLOB SFNTLY_DATA_FILES src/sfntly/data/*.h src/sfntly/data/*.cc)
+  file(GLOB SFNTLY_MATH_FILES src/sfntly/math/*.h src/sfntly/math/*.cc)
+  file(GLOB SFNTLY_TABLE_COMMON_FILES src/sfntly/table/*.h src/sfntly/table/*.cc)
+  file(GLOB SFNTLY_TABLE_BITMAP_FILES src/sfntly/table/bitmap/*.h src/sfntly/table/bitmap/*.cc)
+  file(GLOB SFNTLY_TABLE_CORE_FILES src/sfntly/table/core/*.h src/sfntly/table/core/*.cc)
+  file(GLOB SFNTLY_TABLE_TTF_FILES src/sfntly/table/truetype/*.h src/sfntly/table/truetype/*.cc)
+  source_group(core FILES ${SFNTLY_CORE_FILES})
+  source_group(ports FILES ${SFNTLY_PORT_FILES})
+  source_group(data FILES ${SFNTLY_DATA_FILES})
+  source_group(math FILES ${SFNTLY_MATH_FILES})
+  source_group(table FILES ${SFNTLY_TABLE_COMMON_FILES})
+  source_group(table\\bitmap FILES ${SFNTLY_TABLE_BITMAP_FILES})
+  source_group(table\\core FILES ${SFNTLY_TABLE_CORE_FILES})
+  source_group(table\\truetype FILES ${SFNTLY_TABLE_TTF_FILES})
+  add_library(sfntly
+              ${SFNTLY_CORE_FILES}
+              ${SFNTLY_PORT_FILES}
+              ${SFNTLY_DATA_FILES}
+              ${SFNTLY_MATH_FILES}
+              ${SFNTLY_TABLE_COMMON_FILES}
+              ${SFNTLY_TABLE_BITMAP_FILES}
+              ${SFNTLY_TABLE_CORE_FILES}
+              ${SFNTLY_TABLE_TTF_FILES})
+  file(GLOB_RECURSE SIMPLE_SUBSETTER src/sample/subsetter/*.h src/sample/subsetter/*.cc
+                                     src/sfntly/tools/*.h src/sfntly/tools/*.cc)
+  add_executable(subsetter ${SIMPLE_SUBSETTER})
+  target_link_libraries(subsetter sfntly icuuc)
+if(CMAKE_COMPILER_IS_GNUCXX)
+  target_link_libraries(subsetter pthread)
+endif(CMAKE_COMPILER_IS_GNUCXX)
+  file(GLOB TINYXML src/test/tinyxml/*.cpp)
+  add_library(tinyxml
+              ${TINYXML})
+  file(GLOB TEST_CASES src/test/*.cc src/test/autogenerated/*.cc)
+  file(GLOB CHROME_SUBSETTER_LIB
+    src/sample/chromium/subsetter_impl.h
+    src/sample/chromium/subsetter_impl.cc
+    src/sample/chromium/font_subsetter.cc
+    src/sample/chromium/font_subsetter.h)
+  add_executable(unit_test
+    ${TEST_CASES} ${CHROME_SUBSETTER_LIB}
+    ext/gtest/src/gtest-all.cc
+    ext/gtest/src/gtest_main.cc)
+  target_link_libraries(unit_test sfntly icuuc tinyxml)
+if(CMAKE_COMPILER_IS_GNUCXX)
+  target_link_libraries(unit_test pthread)
+endif(CMAKE_COMPILER_IS_GNUCXX)
+  # subtly targets
+  file(GLOB SUBTLY_FILES src/sample/subtly/*.h src/sample/subtly/*.cc)
+  file(GLOB SUBTLY_MAINS src/sample/subtly/*main.cc)
+  list(REMOVE_ITEM SUBTLY_FILES ${SUBTLY_MAINS})
+  add_library(subtly
+    ${SUBTLY_FILES})
+  add_executable(subtly_subsetter
+    src/sample/subtly/subsetter_main.cc)
+  target_link_libraries(subtly_subsetter subtly sfntly icuuc)
+if(CMAKE_COMPILER_IS_GNUCXX)
+  target_link_libraries(subtly_subsetter pthread)
+endif(CMAKE_COMPILER_IS_GNUCXX)
+  add_executable(subtly_merger
+    src/sample/subtly/merger_main.cc)
+  target_link_libraries(subtly_merger subtly sfntly icuuc)
+if(CMAKE_COMPILER_IS_GNUCXX)
+  target_link_libraries(subtly_merger pthread)
+endif(CMAKE_COMPILER_IS_GNUCXX)
+  add_executable(subtly_debug
+    src/sample/subtly/debug_main.cc)
+  target_link_libraries(subtly_debug subtly sfntly icuuc)
+if(CMAKE_COMPILER_IS_GNUCXX)
+  target_link_libraries(subtly_debug pthread)
+endif(CMAKE_COMPILER_IS_GNUCXX)
+   add_executable(chrome_subsetter
+     ${CHROME_SUBSETTER_LIB}
+     src/sample/chromium/chrome_subsetter.cc
+   )
+   target_link_libraries(chrome_subsetter sfntly icuuc)
+ if(CMAKE_COMPILER_IS_GNUCXX)
+   target_link_libraries(chrome_subsetter pthread)
+ endif(CMAKE_COMPILER_IS_GNUCXX)
diff --git a/sfntly/cpp/COPYING.txt b/sfntly/cpp/COPYING.txt
new file mode 100644
index 0000000..c61423c
--- /dev/null
+++ b/sfntly/cpp/COPYING.txt
@@ -0,0 +1,203 @@
+
+                                 Apache License
+                           Version 2.0, January 2004
+                        http://www.apache.org/licenses/
+
+   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
+
+   1. Definitions.
+
+      "License" shall mean the terms and conditions for use, reproduction,
+      and distribution as defined by Sections 1 through 9 of this document.
+
+      "Licensor" shall mean the copyright owner or entity authorized by
+      the copyright owner that is granting the License.
+
+      "Legal Entity" shall mean the union of the acting entity and all
+      other entities that control, are controlled by, or are under common
+      control with that entity. For the purposes of this definition,
+      "control" means (i) the power, direct or indirect, to cause the
+      direction or management of such entity, whether by contract or
+      otherwise, or (ii) ownership of fifty percent (50%) or more of the
+      outstanding shares, or (iii) beneficial ownership of such entity.
+
+      "You" (or "Your") shall mean an individual or Legal Entity
+      exercising permissions granted by this License.
+
+      "Source" form shall mean the preferred form for making modifications,
+      including but not limited to software source code, documentation
+      source, and configuration files.
+
+      "Object" form shall mean any form resulting from mechanical
+      transformation or translation of a Source form, including but
+      not limited to compiled object code, generated documentation,
+      and conversions to other media types.
+
+      "Work" shall mean the work of authorship, whether in Source or
+      Object form, made available under the License, as indicated by a
+      copyright notice that is included in or attached to the work
+      (an example is provided in the Appendix below).
+
+      "Derivative Works" shall mean any work, whether in Source or Object
+      form, that is based on (or derived from) the Work and for which the
+      editorial revisions, annotations, elaborations, or other modifications
+      represent, as a whole, an original work of authorship. For the purposes
+      of this License, Derivative Works shall not include works that remain
+      separable from, or merely link (or bind by name) to the interfaces of,
+      the Work and Derivative Works thereof.
+
+      "Contribution" shall mean any work of authorship, including
+      the original version of the Work and any modifications or additions
+      to that Work or Derivative Works thereof, that is intentionally
+      submitted to Licensor for inclusion in the Work by the copyright owner
+      or by an individual or Legal Entity authorized to submit on behalf of
+      the copyright owner. For the purposes of this definition, "submitted"
+      means any form of electronic, verbal, or written communication sent
+      to the Licensor or its representatives, including but not limited to
+      communication on electronic mailing lists, source code control systems,
+      and issue tracking systems that are managed by, or on behalf of, the
+      Licensor for the purpose of discussing and improving the Work, but
+      excluding communication that is conspicuously marked or otherwise
+      designated in writing by the copyright owner as "Not a Contribution."
+
+      "Contributor" shall mean Licensor and any individual or Legal Entity
+      on behalf of whom a Contribution has been received by Licensor and
+      subsequently incorporated within the Work.
+
+   2. Grant of Copyright License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      copyright license to reproduce, prepare Derivative Works of,
+      publicly display, publicly perform, sublicense, and distribute the
+      Work and such Derivative Works in Source or Object form.
+
+   3. Grant of Patent License. Subject to the terms and conditions of
+      this License, each Contributor hereby grants to You a perpetual,
+      worldwide, non-exclusive, no-charge, royalty-free, irrevocable
+      (except as stated in this section) patent license to make, have made,
+      use, offer to sell, sell, import, and otherwise transfer the Work,
+      where such license applies only to those patent claims licensable
+      by such Contributor that are necessarily infringed by their
+      Contribution(s) alone or by combination of their Contribution(s)
+      with the Work to which such Contribution(s) was submitted. If You
+      institute patent litigation against any entity (including a
+      cross-claim or counterclaim in a lawsuit) alleging that the Work
+      or a Contribution incorporated within the Work constitutes direct
+      or contributory patent infringement, then any patent licenses
+      granted to You under this License for that Work shall terminate
+      as of the date such litigation is filed.
+
+   4. Redistribution. You may reproduce and distribute copies of the
+      Work or Derivative Works thereof in any medium, with or without
+      modifications, and in Source or Object form, provided that You
+      meet the following conditions:
+
+      (a) You must give any other recipients of the Work or
+          Derivative Works a copy of this License; and
+
+      (b) You must cause any modified files to carry prominent notices
+          stating that You changed the files; and
+
+      (c) You must retain, in the Source form of any Derivative Works
+          that You distribute, all copyright, patent, trademark, and
+          attribution notices from the Source form of the Work,
+          excluding those notices that do not pertain to any part of
+          the Derivative Works; and
+
+      (d) If the Work includes a "NOTICE" text file as part of its
+          distribution, then any Derivative Works that You distribute must
+          include a readable copy of the attribution notices contained
+          within such NOTICE file, excluding those notices that do not
+          pertain to any part of the Derivative Works, in at least one
+          of the following places: within a NOTICE text file distributed
+          as part of the Derivative Works; within the Source form or
+          documentation, if provided along with the Derivative Works; or,
+          within a display generated by the Derivative Works, if and
+          wherever such third-party notices normally appear. The contents
+          of the NOTICE file are for informational purposes only and
+          do not modify the License. You may add Your own attribution
+          notices within Derivative Works that You distribute, alongside
+          or as an addendum to the NOTICE text from the Work, provided
+          that such additional attribution notices cannot be construed
+          as modifying the License.
+
+      You may add Your own copyright statement to Your modifications and
+      may provide additional or different license terms and conditions
+      for use, reproduction, or distribution of Your modifications, or
+      for any such Derivative Works as a whole, provided Your use,
+      reproduction, and distribution of the Work otherwise complies with
+      the conditions stated in this License.
+
+   5. Submission of Contributions. Unless You explicitly state otherwise,
+      any Contribution intentionally submitted for inclusion in the Work
+      by You to the Licensor shall be under the terms and conditions of
+      this License, without any additional terms or conditions.
+      Notwithstanding the above, nothing herein shall supersede or modify
+      the terms of any separate license agreement you may have executed
+      with Licensor regarding such Contributions.
+
+   6. Trademarks. This License does not grant permission to use the trade
+      names, trademarks, service marks, or product names of the Licensor,
+      except as required for reasonable and customary use in describing the
+      origin of the Work and reproducing the content of the NOTICE file.
+
+   7. Disclaimer of Warranty. Unless required by applicable law or
+      agreed to in writing, Licensor provides the Work (and each
+      Contributor provides its Contributions) on an "AS IS" BASIS,
+      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+      implied, including, without limitation, any warranties or conditions
+      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
+      PARTICULAR PURPOSE. You are solely responsible for determining the
+      appropriateness of using or redistributing the Work and assume any
+      risks associated with Your exercise of permissions under this License.
+
+   8. Limitation of Liability. In no event and under no legal theory,
+      whether in tort (including negligence), contract, or otherwise,
+      unless required by applicable law (such as deliberate and grossly
+      negligent acts) or agreed to in writing, shall any Contributor be
+      liable to You for damages, including any direct, indirect, special,
+      incidental, or consequential damages of any character arising as a
+      result of this License or out of the use or inability to use the
+      Work (including but not limited to damages for loss of goodwill,
+      work stoppage, computer failure or malfunction, or any and all
+      other commercial damages or losses), even if such Contributor
+      has been advised of the possibility of such damages.
+
+   9. Accepting Warranty or Additional Liability. While redistributing
+      the Work or Derivative Works thereof, You may choose to offer,
+      and charge a fee for, acceptance of support, warranty, indemnity,
+      or other liability obligations and/or rights consistent with this
+      License. However, in accepting such obligations, You may act only
+      on Your own behalf and on Your sole responsibility, not on behalf
+      of any other Contributor, and only if You agree to indemnify,
+      defend, and hold each Contributor harmless for any liability
+      incurred by, or claims asserted against, such Contributor by reason
+      of your accepting any such warranty or additional liability.
+
+   END OF TERMS AND CONDITIONS
+
+   APPENDIX: How to apply the Apache License to your work.
+
+      To apply the Apache License to your work, attach the following
+      boilerplate notice, with the fields enclosed by brackets "[]"
+      replaced with your own identifying information. (Don't include
+      the brackets!)  The text should be enclosed in the appropriate
+      comment syntax for the file format. We also recommend that a
+      file or class name and description of purpose be included on the
+      same "printed page" as the copyright notice for easier
+      identification within third-party archives.
+
+   Copyright 2011 Google Inc. All Rights Reserved.
+
+   Licensed under the Apache License, Version 2.0 (the "License");
+   you may not use this file except in compliance with the License.
+   You may obtain a copy of the License at
+
+       http://www.apache.org/licenses/LICENSE-2.0
+
+   Unless required by applicable law or agreed to in writing, software
+   distributed under the License is distributed on an "AS IS" BASIS,
+   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+   See the License for the specific language governing permissions and
+   limitations under the License.
+
diff --git a/sfntly/cpp/README.txt b/sfntly/cpp/README.txt
new file mode 100644
index 0000000..ac2b43a
--- /dev/null
+++ b/sfntly/cpp/README.txt
@@ -0,0 +1,3 @@
+Please refer to http://code.google.com/p/sfntly/wiki/build_cpp regarding how to build sfntly.
+
+sfntly wiki contains other useful documents: http://code.google.com/p/sfntly/w/list
\ No newline at end of file
diff --git a/sfntly/cpp/src/sample/chromium/chrome_subsetter.cc b/sfntly/cpp/src/sample/chromium/chrome_subsetter.cc
new file mode 100644
index 0000000..df15c18
--- /dev/null
+++ b/sfntly/cpp/src/sample/chromium/chrome_subsetter.cc
@@ -0,0 +1,131 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+
+#include <vector>
+#include <string>
+#include <sstream>
+
+#include "sfntly/port/type.h"
+#include "font_subsetter.h"
+
+template <typename T>
+class HexTo {
+ public:
+  explicit HexTo(const char* in) {
+    std::stringstream ss;
+    ss << std::hex << in;
+    ss >> value_;
+  }
+  operator T() const { return value_; }
+
+ private:
+  T value_;
+};
+
+bool LoadFile(const char* input_file_path, sfntly::ByteVector* input_buffer) {
+  assert(input_file_path);
+  assert(input_buffer);
+
+  FILE* input_file = NULL;
+#if defined WIN32
+  fopen_s(&input_file, input_file_path, "rb");
+#else
+  input_file = fopen(input_file_path, "rb");
+#endif
+  if (input_file == NULL) {
+    return false;
+  }
+  fseek(input_file, 0, SEEK_END);
+  size_t file_size = ftell(input_file);
+  fseek(input_file, 0, SEEK_SET);
+  input_buffer->resize(file_size);
+  size_t bytes_read = fread(&((*input_buffer)[0]), 1, file_size, input_file);
+  fclose(input_file);
+  return bytes_read == file_size;
+}
+
+bool SaveFile(const char* output_file_path, const unsigned char* output_buffer,
+              int buffer_length) {
+  int byte_count = 0;
+  if (buffer_length > 0) {
+    FILE* output_file = NULL;
+#if defined WIN32
+    fopen_s(&output_file, output_file_path, "wb");
+#else
+    output_file = fopen(output_file_path, "wb");
+#endif
+    if (output_file) {
+      byte_count = fwrite(output_buffer, 1, buffer_length, output_file);
+      fflush(output_file);
+      fclose(output_file);
+    }
+    return buffer_length == byte_count;
+  }
+  return false;
+}
+
+bool StringToGlyphId(const char* input, std::vector<unsigned int>* glyph_ids) {
+  assert(input);
+  std::string hex_csv = input;
+  size_t start = 0;
+  size_t end = hex_csv.find_first_of(",");
+  while (end != std::string::npos) {
+    glyph_ids->push_back(
+        HexTo<unsigned int>(hex_csv.substr(start, end - start).c_str()));
+    start = end + 1;
+    end = hex_csv.find_first_of(",", start);
+  }
+  glyph_ids->push_back(HexTo<unsigned int>(hex_csv.substr(start).c_str()));
+  return glyph_ids->size() > 0;
+}
+
+int main(int argc, char** argv) {
+  if (argc < 5) {
+    fprintf(stderr,
+        "Usage: %s <input path> <output path> <font name> <glyph ids>\n",
+        argv[0]);
+    fprintf(stderr, "\tGlyph ids are comma separated hex values\n");
+    fprintf(stderr, "\te.g. 20,1a,3b,4f\n");
+    return 0;
+  }
+
+  sfntly::ByteVector input_buffer;
+  if (!LoadFile(argv[1], &input_buffer)) {
+    fprintf(stderr, "ERROR: unable to load font file %s\n", argv[1]);
+    return 0;
+  }
+
+  std::vector<unsigned int> glyph_ids;
+  if (!StringToGlyphId(argv[4], &glyph_ids)) {
+    fprintf(stderr, "ERROR: unable to parse input glyph id\n");
+    return 0;
+  }
+
+  unsigned char* output_buffer = NULL;
+  int output_length =
+      SfntlyWrapper::SubsetFont(argv[3],
+                                &(input_buffer[0]),
+                                input_buffer.size(),
+                                &(glyph_ids[0]),
+                                glyph_ids.size(),
+                                &output_buffer);
+
+  int result = SaveFile(argv[2], output_buffer, output_length) ? 1 : 0;
+  delete[] output_buffer;
+  return result;
+}
diff --git a/sfntly/cpp/src/sample/chromium/font_subsetter.cc b/sfntly/cpp/src/sample/chromium/font_subsetter.cc
new file mode 100644
index 0000000..14f5494
--- /dev/null
+++ b/sfntly/cpp/src/sample/chromium/font_subsetter.cc
@@ -0,0 +1,39 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "font_subsetter.h"
+
+#include "subsetter_impl.h"
+
+int SfntlyWrapper::SubsetFont(const char* font_name,
+                              const unsigned char* original_font,
+                              size_t font_size,
+                              const unsigned int* glyph_ids,
+                              size_t glyph_count,
+                              unsigned char** output_buffer) {
+  if (output_buffer == NULL ||
+      original_font == NULL || font_size == 0 ||
+      glyph_ids == NULL || glyph_count == 0) {
+    return 0;
+  }
+
+  sfntly::SubsetterImpl subsetter;
+  if (!subsetter.LoadFont(font_name, original_font, font_size)) {
+    return -1;  // Load error or font not found.
+  }
+
+  return subsetter.SubsetFont(glyph_ids, glyph_count, output_buffer);
+}
diff --git a/sfntly/cpp/src/sample/chromium/font_subsetter.h b/sfntly/cpp/src/sample/chromium/font_subsetter.h
new file mode 100644
index 0000000..07b1b5b
--- /dev/null
+++ b/sfntly/cpp/src/sample/chromium/font_subsetter.h
@@ -0,0 +1,51 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+// File is originally from Chromium third_party/sfntly/src/subsetter.
+// Use as test case in sfntly so that problems can be caught in upstream early.
+#ifndef SFNTLY_CPP_SRC_TEST_FONT_SUBSETTER_H_
+#define SFNTLY_CPP_SRC_TEST_FONT_SUBSETTER_H_
+
+#include <cstddef>
+
+class SfntlyWrapper {
+ public:
+
+  // Font subsetting API
+  //
+  // Input TTF/TTC/OTF fonts, specify the glyph IDs to subset, and the subset
+  // font is returned in |output_buffer| (caller to delete[]).  Return value is
+  // the length of output_buffer allocated.
+  //
+  // If subsetting fails, a negative value is returned.  If none of the glyph
+  // IDs specified is found, the function will return 0.
+  //
+  // |font_name|      Font name, required for TTC files.  If specified NULL,
+  //                  the first available font is selected.
+  // |original_font|  Original font file contents.
+  // |font_size|      Size of |original_font| in bytes.
+  // |glyph_ids|      Glyph IDs to subset.  If the specified glyph ID is not
+  //                  found in the font file, it will be ignored silently.
+  // |glyph_count|    Number of glyph IDs in |glyph_ids|
+  // |output_buffer|  Generated subset font.  Caller to delete[].
+  static int SubsetFont(const char* font_name,
+                        const unsigned char* original_font,
+                        size_t font_size,
+                        const unsigned int* glyph_ids,
+                        size_t glyph_count,
+                        unsigned char** output_buffer);
+};
+
+#endif  // SFNTLY_CPP_SRC_TEST_FONT_SUBSETTER_H_
diff --git a/sfntly/cpp/src/sample/chromium/subsetter_impl.cc b/sfntly/cpp/src/sample/chromium/subsetter_impl.cc
new file mode 100644
index 0000000..528e336
--- /dev/null
+++ b/sfntly/cpp/src/sample/chromium/subsetter_impl.cc
@@ -0,0 +1,785 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "subsetter_impl.h"
+
+#include <string.h>
+
+#include <algorithm>
+#include <iterator>
+#include <map>
+#include <set>
+
+#include "sfntly/table/bitmap/eblc_table.h"
+#include "sfntly/table/bitmap/ebdt_table.h"
+#include "sfntly/table/bitmap/index_sub_table.h"
+#include "sfntly/table/bitmap/index_sub_table_format1.h"
+#include "sfntly/table/bitmap/index_sub_table_format2.h"
+#include "sfntly/table/bitmap/index_sub_table_format3.h"
+#include "sfntly/table/bitmap/index_sub_table_format4.h"
+#include "sfntly/table/bitmap/index_sub_table_format5.h"
+#include "sfntly/table/core/name_table.h"
+#include "sfntly/tag.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/port/memory_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+
+#if defined U_USING_ICU_NAMESPACE
+  U_NAMESPACE_USE
+#endif
+
+namespace {
+
+using namespace sfntly;
+
+// The bitmap tables must be greater than 16KB to trigger bitmap subsetter.
+static const int BITMAP_SIZE_THRESHOLD = 16384;
+
+void ConstructName(UChar* name_part, UnicodeString* name, int32_t name_id) {
+  switch (name_id) {
+    case NameId::kFullFontName:
+      *name = name_part;
+      break;
+    case NameId::kFontFamilyName:
+    case NameId::kPreferredFamily:
+    case NameId::kWWSFamilyName: {
+      UnicodeString original = *name;
+      *name = name_part;
+      *name += original;
+      break;
+    }
+    case NameId::kFontSubfamilyName:
+    case NameId::kPreferredSubfamily:
+    case NameId::kWWSSubfamilyName:
+      *name += name_part;
+      break;
+    default:
+      // This name part is not used to construct font name (e.g. copyright).
+      // Simply ignore it.
+      break;
+  }
+}
+
+int32_t HashCode(int32_t platform_id, int32_t encoding_id, int32_t language_id,
+                 int32_t name_id) {
+  int32_t result = platform_id << 24 | encoding_id << 16 | language_id << 8;
+  if (name_id == NameId::kFullFontName) {
+    result |= 0xff;
+  } else if (name_id == NameId::kPreferredFamily ||
+             name_id == NameId::kPreferredSubfamily) {
+    result |= 0xf;
+  } else if (name_id == NameId::kWWSFamilyName ||
+             name_id == NameId::kWWSSubfamilyName) {
+    result |= 1;
+  }
+  return result;
+}
+
+bool HasName(const char* font_name, Font* font) {
+  UnicodeString font_string = UnicodeString::fromUTF8(font_name);
+  if (font_string.isEmpty())
+    return false;
+  UnicodeString regular_suffix = UnicodeString::fromUTF8(" Regular");
+  UnicodeString alt_font_string = font_string;
+  alt_font_string += regular_suffix;
+
+  typedef std::map<int32_t, UnicodeString> NameMap;
+  NameMap names;
+  NameTablePtr name_table = down_cast<NameTable*>(font->GetTable(Tag::name));
+  if (name_table == NULL) {
+    return false;
+  }
+
+  for (int32_t i = 0; i < name_table->NameCount(); ++i) {
+    switch (name_table->NameId(i)) {
+      case NameId::kFontFamilyName:
+      case NameId::kFontSubfamilyName:
+      case NameId::kFullFontName:
+      case NameId::kPreferredFamily:
+      case NameId::kPreferredSubfamily:
+      case NameId::kWWSFamilyName:
+      case NameId::kWWSSubfamilyName: {
+        UChar* name_part = name_table->Name(i);
+        if (name_part == NULL) {
+          continue;
+        }
+        int32_t hash_code = HashCode(name_table->PlatformId(i),
+                                     name_table->EncodingId(i),
+                                     name_table->LanguageId(i),
+                                     name_table->NameId(i));
+        ConstructName(name_part, &(names[hash_code]), name_table->NameId(i));
+        delete[] name_part;
+        break;
+      }
+      default:
+        break;
+    }
+  }
+
+  if (!names.empty()) {
+    for (NameMap::iterator i = names.begin(), e = names.end(); i != e; ++i) {
+      if (i->second.caseCompare(font_string, 0) == 0 ||
+          i->second.caseCompare(alt_font_string, 0) == 0) {
+        return true;
+      }
+    }
+  }
+  return false;
+}
+
+Font* FindFont(const char* font_name, const FontArray& font_array) {
+  if (font_array.empty() || font_array[0] == NULL) {
+    return NULL;
+  }
+
+  if (font_name && strlen(font_name)) {
+    for (FontArray::const_iterator i = font_array.begin(), e = font_array.end();
+         i != e; ++i) {
+      if (HasName(font_name, i->p_)) {
+        return i->p_;
+      }
+    }
+  }
+
+  return font_array[0].p_;
+}
+
+bool ResolveCompositeGlyphs(GlyphTable* glyph_table,
+                            LocaTable* loca_table,
+                            const unsigned int* glyph_ids,
+                            size_t glyph_count,
+                            IntegerSet* glyph_id_processed) {
+  if (glyph_table == NULL || loca_table == NULL ||
+      glyph_ids == NULL || glyph_count == 0 || glyph_id_processed == NULL) {
+    return false;
+  }
+
+  // Sort and uniquify glyph ids.
+  IntegerSet glyph_id_remaining;
+  glyph_id_remaining.insert(0);  // Always include glyph id 0.
+  for (size_t i = 0; i < glyph_count; ++i) {
+    glyph_id_remaining.insert(glyph_ids[i]);
+  }
+
+  // Identify if any given glyph id maps to a composite glyph.  If so, include
+  // the glyphs referenced by that composite glyph.
+  while (!glyph_id_remaining.empty()) {
+    IntegerSet comp_glyph_id;
+    for (IntegerSet::iterator i = glyph_id_remaining.begin(),
+                              e = glyph_id_remaining.end(); i != e; ++i) {
+      if (*i < 0 || *i >= loca_table->num_glyphs()) {
+        // Invalid glyph id, ignore.
+        continue;
+      }
+
+      int32_t length = loca_table->GlyphLength(*i);
+      if (length == 0) {
+        // Empty glyph, ignore.
+        continue;
+      }
+      int32_t offset = loca_table->GlyphOffset(*i);
+
+      GlyphPtr glyph;
+      glyph.Attach(glyph_table->GetGlyph(offset, length));
+      if (glyph == NULL) {
+        // Error finding glyph, ignore.
+        continue;
+      }
+
+      if (glyph->GlyphType() == GlyphType::kComposite) {
+        Ptr<GlyphTable::CompositeGlyph> comp_glyph =
+            down_cast<GlyphTable::CompositeGlyph*>(glyph.p_);
+        for (int32_t j = 0; j < comp_glyph->NumGlyphs(); ++j) {
+          int32_t glyph_id = comp_glyph->GlyphIndex(j);
+          if (glyph_id_processed->find(glyph_id) == glyph_id_processed->end() &&
+              glyph_id_remaining.find(glyph_id) == glyph_id_remaining.end()) {
+            comp_glyph_id.insert(comp_glyph->GlyphIndex(j));
+          }
+        }
+      }
+
+      glyph_id_processed->insert(*i);
+    }
+
+    glyph_id_remaining.clear();
+    glyph_id_remaining = comp_glyph_id;
+  }
+
+  return true;
+}
+
+bool SetupGlyfBuilders(Font::Builder* font_builder,
+                       GlyphTable* glyph_table,
+                       LocaTable* loca_table,
+                       const IntegerSet& glyph_ids) {
+  if (!font_builder || !glyph_table || !loca_table) {
+    return false;
+  }
+
+  GlyphTableBuilderPtr glyph_table_builder =
+      down_cast<GlyphTable::Builder*>(font_builder->NewTableBuilder(Tag::glyf));
+  LocaTableBuilderPtr loca_table_builder =
+      down_cast<LocaTable::Builder*>(font_builder->NewTableBuilder(Tag::loca));
+  if (glyph_table_builder == NULL || loca_table_builder == NULL) {
+    // Out of memory.
+    return false;
+  }
+
+  // Extract glyphs and setup loca list.
+  IntegerList loca_list;
+  loca_list.resize(loca_table->num_glyphs());
+  loca_list.push_back(0);
+  int32_t last_glyph_id = 0;
+  int32_t last_offset = 0;
+  GlyphTable::GlyphBuilderList* glyph_builders =
+      glyph_table_builder->GlyphBuilders();
+  for (IntegerSet::const_iterator i = glyph_ids.begin(), e = glyph_ids.end();
+                                  i != e; ++i) {
+    int32_t length = loca_table->GlyphLength(*i);
+    int32_t offset = loca_table->GlyphOffset(*i);
+
+    GlyphPtr glyph;
+    glyph.Attach(glyph_table->GetGlyph(offset, length));
+
+    // Add glyph to new glyf table.
+    ReadableFontDataPtr data = glyph->ReadFontData();
+    WritableFontDataPtr copy_data;
+    copy_data.Attach(WritableFontData::CreateWritableFontData(data->Length()));
+    data->CopyTo(copy_data);
+    GlyphBuilderPtr glyph_builder;
+    glyph_builder.Attach(glyph_table_builder->GlyphBuilder(copy_data));
+    glyph_builders->push_back(glyph_builder);
+
+    // Configure loca list.
+    for (int32_t j = last_glyph_id + 1; j <= *i; ++j) {
+      loca_list[j] = last_offset;
+    }
+    last_offset += length;
+    loca_list[*i + 1] = last_offset;
+    last_glyph_id = *i;
+  }
+  for (int32_t j = last_glyph_id + 1; j <= loca_table->num_glyphs(); ++j) {
+    loca_list[j] = last_offset;
+  }
+  loca_table_builder->SetLocaList(&loca_list);
+
+  return true;
+}
+
+bool HasOverlap(int32_t range_begin, int32_t range_end,
+                const IntegerSet& glyph_ids) {
+  if (range_begin == range_end) {
+    return glyph_ids.find(range_begin) != glyph_ids.end();
+  } else if (range_end > range_begin) {
+    IntegerSet::const_iterator left = glyph_ids.lower_bound(range_begin);
+    IntegerSet::const_iterator right = glyph_ids.lower_bound(range_end);
+    return right != left;
+  }
+  return false;
+}
+
+// Initialize builder, returns false if glyph_id subset is not covered.
+// Not thread-safe, caller to ensure object life-time.
+bool InitializeBitmapBuilder(EbdtTable::Builder* ebdt, EblcTable::Builder* eblc,
+                             const IntegerSet& glyph_ids) {
+  BitmapLocaList loca_list;
+  BitmapSizeTableBuilderList* strikes = eblc->BitmapSizeBuilders();
+
+  // Note: Do not call eblc_builder->GenerateLocaList(&loca_list) and then
+  //       ebdt_builder->SetLoca(loca_list).  For fonts like SimSun, there are
+  //       >28K glyphs inside, where a typical usage will be <1K glyphs.  Doing
+  //       the calls improperly will result in creation of >100K objects that
+  //       will be destroyed immediately, inducing significant slowness.
+  IntegerList removed_strikes;
+  for (size_t i = 0; i < strikes->size(); i++) {
+    if (!HasOverlap((*strikes)[i]->StartGlyphIndex(),
+                    (*strikes)[i]->EndGlyphIndex(), glyph_ids)) {
+      removed_strikes.push_back(i);
+      continue;
+    }
+
+    IndexSubTableBuilderList* index_builders =
+        (*strikes)[i]->IndexSubTableBuilders();
+    IntegerList removed_indexes;
+    BitmapGlyphInfoMap info_map;
+    for (size_t j = 0; j < index_builders->size(); ++j) {
+      if ((*index_builders)[j] == NULL) {
+        // Subtable is malformed, let's just skip it.
+        removed_indexes.push_back(j);
+        continue;
+      }
+      int32_t first_glyph_id = (*index_builders)[j]->first_glyph_index();
+      int32_t last_glyph_id = (*index_builders)[j]->last_glyph_index();
+      if (!HasOverlap(first_glyph_id, last_glyph_id, glyph_ids)) {
+        removed_indexes.push_back(j);
+        continue;
+      }
+      for (IntegerSet::const_iterator gid = glyph_ids.begin(),
+                                      gid_end = glyph_ids.end();
+                                      gid != gid_end; gid++) {
+        if (*gid < first_glyph_id) {
+          continue;
+        }
+        if (*gid > last_glyph_id) {
+          break;
+        }
+        BitmapGlyphInfoPtr info;
+        info.Attach((*index_builders)[j]->GlyphInfo(*gid));
+        if (info && info->length()) {  // Do not include gid without bitmap
+          info_map[*gid] = info;
+        }
+      }
+    }
+    if (!info_map.empty()) {
+      loca_list.push_back(info_map);
+    } else {
+      removed_strikes.push_back(i);  // Detected null entries.
+    }
+
+    // Remove unused index sub tables
+    for (IntegerList::reverse_iterator j = removed_indexes.rbegin(),
+                                       e = removed_indexes.rend();
+                                       j != e; j++) {
+      index_builders->erase(index_builders->begin() + *j);
+    }
+  }
+  if (removed_strikes.size() == strikes->size() || loca_list.empty()) {
+    return false;
+  }
+
+  for (IntegerList::reverse_iterator i = removed_strikes.rbegin(),
+                                     e = removed_strikes.rend(); i != e; i++) {
+    strikes->erase(strikes->begin() + *i);
+  }
+
+  if (strikes->empty()) {  // no glyph covered, can safely drop the builders.
+    return false;
+  }
+
+  ebdt->SetLoca(&loca_list);
+  ebdt->GlyphBuilders();  // Initialize the builder.
+  return true;
+}
+
+void CopyBigGlyphMetrics(BigGlyphMetrics::Builder* source,
+                         BigGlyphMetrics::Builder* target) {
+  target->SetHeight(static_cast<byte_t>(source->Height()));
+  target->SetWidth(static_cast<byte_t>(source->Width()));
+  target->SetHoriBearingX(static_cast<byte_t>(source->HoriBearingX()));
+  target->SetHoriBearingY(static_cast<byte_t>(source->HoriBearingY()));
+  target->SetHoriAdvance(static_cast<byte_t>(source->HoriAdvance()));
+  target->SetVertBearingX(static_cast<byte_t>(source->VertBearingX()));
+  target->SetVertBearingY(static_cast<byte_t>(source->VertBearingY()));
+  target->SetVertAdvance(static_cast<byte_t>(source->VertAdvance()));
+}
+
+CALLER_ATTACH IndexSubTable::Builder*
+ConstructIndexFormat4(IndexSubTable::Builder* b, const BitmapGlyphInfoMap& loca,
+                      int32_t* image_data_offset) {
+  IndexSubTableFormat4BuilderPtr builder4;
+  builder4.Attach(IndexSubTableFormat4::Builder::CreateBuilder());
+  CodeOffsetPairBuilderList offset_pairs;
+
+  size_t offset = 0;
+  int32_t lower_bound = b->first_glyph_index();
+  int32_t upper_bound = b->last_glyph_index();
+  int32_t last_gid = -1;
+  BitmapGlyphInfoMap::const_iterator i = loca.lower_bound(lower_bound);
+  BitmapGlyphInfoMap::const_iterator end = loca.end();
+  if (i != end) {
+    last_gid = i->first;
+    builder4->set_first_glyph_index(last_gid);
+    builder4->set_image_format(b->image_format());
+    builder4->set_image_data_offset(*image_data_offset);
+  }
+  for (; i != end; i++) {
+    int32_t gid = i->first;
+    if (gid > upper_bound) {
+      break;
+    }
+    offset_pairs.push_back(
+        IndexSubTableFormat4::CodeOffsetPairBuilder(gid, offset));
+    offset += i->second->length();
+    last_gid = gid;
+  }
+  offset_pairs.push_back(
+      IndexSubTableFormat4::CodeOffsetPairBuilder(-1, offset));
+  builder4->set_last_glyph_index(last_gid);
+  *image_data_offset += offset;
+  builder4->SetOffsetArray(offset_pairs);
+
+  return builder4.Detach();
+}
+
+CALLER_ATTACH IndexSubTable::Builder*
+ConstructIndexFormat5(IndexSubTable::Builder* b, const BitmapGlyphInfoMap& loca,
+                      int32_t* image_data_offset) {
+  IndexSubTableFormat5BuilderPtr new_builder;
+  new_builder.Attach(IndexSubTableFormat5::Builder::CreateBuilder());
+
+  // Copy BigMetrics
+  int32_t image_size = 0;
+  if (b->index_format() == IndexSubTable::Format::FORMAT_2) {
+    IndexSubTableFormat2BuilderPtr builder2 =
+      down_cast<IndexSubTableFormat2::Builder*>(b);
+    CopyBigGlyphMetrics(builder2->BigMetrics(), new_builder->BigMetrics());
+    image_size = builder2->ImageSize();
+  } else {
+    IndexSubTableFormat5BuilderPtr builder5 =
+      down_cast<IndexSubTableFormat5::Builder*>(b);
+    BigGlyphMetricsBuilderPtr metrics_builder;
+    CopyBigGlyphMetrics(builder5->BigMetrics(), new_builder->BigMetrics());
+    image_size = builder5->ImageSize();
+  }
+
+  IntegerList* glyph_array = new_builder->GlyphArray();
+  size_t offset = 0;
+  int32_t lower_bound = b->first_glyph_index();
+  int32_t upper_bound = b->last_glyph_index();
+  int32_t last_gid = -1;
+  BitmapGlyphInfoMap::const_iterator i = loca.lower_bound(lower_bound);
+  BitmapGlyphInfoMap::const_iterator end = loca.end();
+  if (i != end) {
+    last_gid = i->first;
+    new_builder->set_first_glyph_index(last_gid);
+    new_builder->set_image_format(b->image_format());
+    new_builder->set_image_data_offset(*image_data_offset);
+    new_builder->SetImageSize(image_size);
+  }
+  for (; i != end; i++) {
+    int32_t gid = i->first;
+    if (gid > upper_bound) {
+      break;
+    }
+    glyph_array->push_back(gid);
+    offset += i->second->length();
+    last_gid = gid;
+  }
+  new_builder->set_last_glyph_index(last_gid);
+  *image_data_offset += offset;
+  return new_builder.Detach();
+}
+
+CALLER_ATTACH IndexSubTable::Builder*
+SubsetIndexSubTable(IndexSubTable::Builder* builder,
+                    const BitmapGlyphInfoMap& loca,
+                    int32_t* image_data_offset) {
+  switch (builder->index_format()) {
+    case IndexSubTable::Format::FORMAT_1:
+    case IndexSubTable::Format::FORMAT_3:
+    case IndexSubTable::Format::FORMAT_4:
+      return ConstructIndexFormat4(builder, loca, image_data_offset);
+    case IndexSubTable::Format::FORMAT_2:
+    case IndexSubTable::Format::FORMAT_5:
+      return ConstructIndexFormat5(builder, loca, image_data_offset);
+    default:
+      assert(false);
+      break;
+  }
+  return NULL;
+}
+
+}
+
+namespace sfntly {
+
+// Not thread-safe, caller to ensure object life-time.
+void SubsetEBLC(EblcTable::Builder* eblc, const BitmapLocaList& new_loca) {
+  BitmapSizeTableBuilderList* size_builders = eblc->BitmapSizeBuilders();
+  if (size_builders == NULL) {
+    return;
+  }
+
+  int32_t image_data_offset = EbdtTable::Offset::kHeaderLength;
+  for (size_t strike = 0; strike < size_builders->size(); ++strike) {
+    IndexSubTableBuilderList* index_builders =
+        (*size_builders)[strike]->IndexSubTableBuilders();
+    for (size_t index = 0; index < index_builders->size(); ++index) {
+      IndexSubTable::Builder* new_builder_raw =
+          SubsetIndexSubTable((*index_builders)[index], new_loca[strike],
+                              &image_data_offset);
+      if (NULL != new_builder_raw) {
+        (*index_builders)[index].Attach(new_builder_raw);
+      }
+    }
+  }
+}
+
+// EBLC structure (from stuartg)
+//  header
+//  bitmapSizeTable[]
+//    one per strike
+//    holds strike metrics - sbitLineMetrics
+//    holds info about indexSubTableArray
+//  indexSubTableArray[][]
+//    one per strike and then one per indexSubTable for that strike
+//    holds info about the indexSubTable
+//    the indexSubTable entries pointed to can be of different formats
+//  indexSubTable
+//    one per indexSubTableArray entry
+//    tells how to get the glyphs
+//    may hold the glyph metrics if they are uniform for all the glyphs in range
+// Please note that the structure can also be
+//  {indexSubTableArray[], indexSubTables[]}[]
+//  This way is also legal and in fact how Microsoft fonts are laid out.
+//
+// There is nothing that says that the indexSubTableArray entries and/or the
+// indexSubTable items need to be unique. They may be shared between strikes.
+//
+// EBDT structure:
+//  header
+//  glyphs
+//    amorphous blob of data
+//    different glyphs that are only able to be figured out from the EBLC table
+//    may hold metrics - depends on the EBLC entry that pointed to them
+
+// Subsetting EBLC table (from arthurhsu)
+//  Most pages use only a fraction (hundreds or less) glyphs out of a given font
+//  (which can have >20K glyphs for CJK).  It's safe to assume that the subset
+//  font will have sparse bitmap glyphs.  So we reconstruct the EBLC table as
+//  format 4 or 5 here.
+
+enum BuildersToRemove {
+  kRemoveNone,
+  kRemoveBDAT,
+  kRemoveBDATAndEBDT,
+  kRemoveEBDT
+};
+
+int SetupBitmapBuilders(Font* font, Font::Builder* font_builder,
+                        const IntegerSet& glyph_ids) {
+  if (!font || !font_builder) {
+    return false;
+  }
+
+  // Check if bitmap table exists.
+  EbdtTablePtr ebdt_table = down_cast<EbdtTable*>(font->GetTable(Tag::EBDT));
+  EblcTablePtr eblc_table = down_cast<EblcTable*>(font->GetTable(Tag::EBLC));
+  bool use_ebdt = (ebdt_table != NULL && eblc_table != NULL);
+  if (!use_ebdt) {
+    ebdt_table = down_cast<EbdtTable*>(font->GetTable(Tag::bdat));
+    eblc_table = down_cast<EblcTable*>(font->GetTable(Tag::bloc));
+    if (ebdt_table == NULL || eblc_table == NULL) {
+      return kRemoveNone;
+    }
+  }
+
+  // If the bitmap table's size is too small, skip subsetting.
+  if (ebdt_table->DataLength() + eblc_table->DataLength() <
+      BITMAP_SIZE_THRESHOLD) {
+    return use_ebdt ? kRemoveBDAT : kRemoveNone;
+  }
+
+  // Get the builders.
+  EbdtTableBuilderPtr ebdt_table_builder = down_cast<EbdtTable::Builder*>(
+      font_builder->NewTableBuilder(use_ebdt ? Tag::EBDT : Tag::bdat,
+                                    ebdt_table->ReadFontData()));
+  EblcTableBuilderPtr eblc_table_builder = down_cast<EblcTable::Builder*>(
+      font_builder->NewTableBuilder(use_ebdt ? Tag::EBLC : Tag::bloc,
+                                    eblc_table->ReadFontData()));
+  if (ebdt_table_builder == NULL || eblc_table_builder == NULL) {
+    // Out of memory.
+    return use_ebdt ? kRemoveBDAT : kRemoveNone;
+  }
+
+  if (!InitializeBitmapBuilder(ebdt_table_builder, eblc_table_builder,
+                               glyph_ids)) {
+    // Bitmap tables do not cover the glyphs in our subset.
+    font_builder->RemoveTableBuilder(use_ebdt ? Tag::EBLC : Tag::bloc);
+    font_builder->RemoveTableBuilder(use_ebdt ? Tag::EBDT : Tag::bdat);
+    return use_ebdt ? kRemoveBDATAndEBDT : kRemoveEBDT;
+  }
+
+  BitmapLocaList new_loca;
+  ebdt_table_builder->GenerateLocaList(&new_loca);
+  SubsetEBLC(eblc_table_builder, new_loca);
+
+  return use_ebdt ? kRemoveBDAT : kRemoveNone;
+}
+
+SubsetterImpl::SubsetterImpl() {
+}
+
+SubsetterImpl::~SubsetterImpl() {
+}
+
+bool SubsetterImpl::LoadFont(const char* font_name,
+                             const unsigned char* original_font,
+                             size_t font_size) {
+  MemoryInputStream mis;
+  mis.Attach(original_font, font_size);
+  if (factory_ == NULL) {
+    factory_.Attach(FontFactory::GetInstance());
+  }
+
+  FontArray font_array;
+  factory_->LoadFonts(&mis, &font_array);
+  font_ = FindFont(font_name, font_array);
+  if (font_ == NULL) {
+    return false;
+  }
+
+  return true;
+}
+
+int SubsetterImpl::SubsetFont(const unsigned int* glyph_ids,
+                              size_t glyph_count,
+                              unsigned char** output_buffer) {
+  if (factory_ == NULL || font_ == NULL) {
+    return -1;
+  }
+
+  // Find glyf and loca table.
+  GlyphTablePtr glyph_table =
+      down_cast<GlyphTable*>(font_->GetTable(Tag::glyf));
+  LocaTablePtr loca_table = down_cast<LocaTable*>(font_->GetTable(Tag::loca));
+  if (glyph_table == NULL || loca_table == NULL) {
+    // We are not able to subset the font.
+    return 0;
+  }
+
+  IntegerSet glyph_id_processed;
+  if (!ResolveCompositeGlyphs(glyph_table, loca_table,
+                              glyph_ids, glyph_count, &glyph_id_processed) ||
+      glyph_id_processed.empty()) {
+    return 0;
+  }
+
+  FontPtr new_font;
+  new_font.Attach(Subset(glyph_id_processed, glyph_table, loca_table));
+  if (new_font == NULL) {
+    return 0;
+  }
+
+  MemoryOutputStream output_stream;
+  factory_->SerializeFont(new_font, &output_stream);
+  int length = static_cast<int>(output_stream.Size());
+  if (length > 0) {
+    *output_buffer = new unsigned char[length];
+    memcpy(*output_buffer, output_stream.Get(), length);
+  }
+
+  return length;
+}
+
+// Long comments regarding TTF tables and PDF (from stuartg)
+//
+// According to PDF spec 1.4 (section 5.8), the following tables must be
+// present:
+//  head, hhea, loca, maxp, cvt, prep, glyf, hmtx, fpgm
+//  cmap if font is used with a simple font dict and not a CIDFont dict
+//
+// Other tables we need to keep for PDF rendering to support zoom in/out:
+//  bdat, bloc, ebdt, eblc, ebsc, gasp
+//
+// Special table:
+//  CFF - if you have this table then you shouldn't have a glyf table and this
+//        is the table with all the glyphs.  Shall skip subsetting completely
+//        since sfntly is not capable of subsetting it for now.
+//  post - extra info here for printing on PostScript printers but maybe not
+//         enough to outweigh the space taken by the names
+//
+// Tables to break apart:
+//  name - could throw away all but one language and one platform strings/ might
+//         throw away some of the name entries
+//  cmap - could strip out non-needed cmap subtables
+//       - format 4 subtable can be subsetted as well using sfntly
+//
+// Graphite tables:
+//  silf, glat, gloc, feat - should be okay to strip out
+//
+// Tables that can be discarded:
+//  OS/2 - everything here is for layout and description of the font that is
+//         elsewhere (some in the PDF objects)
+//  BASE, GDEF, GSUB, GPOS, JSTF - all used for layout
+//  kern - old style layout
+//  DSIG - this will be invalid after subsetting
+//  hdmx - layout
+//  PCLT - metadata that's not needed
+//  vmtx - layout
+//  vhea - layout
+//  VDMX
+//  VORG - not used by TT/OT - used by CFF
+//  hsty - would be surprised to see one of these - used on the Newton
+//  AAT tables - mort, morx, feat, acnt, bsin, just, lcar, fdsc, fmtx, prop,
+//               Zapf, opbd, trak, fvar, gvar, avar, cvar
+//             - these are all layout tables and once layout happens are not
+//               needed anymore
+//  LTSH - layout
+
+CALLER_ATTACH
+Font* SubsetterImpl::Subset(const IntegerSet& glyph_ids, GlyphTable* glyf,
+                            LocaTable* loca) {
+  // The const is initialized here to workaround VC bug of rendering all Tag::*
+  // as 0.  These tags represents the TTF tables that we will embed in subset
+  // font.
+  const int32_t TABLES_IN_SUBSET[] = {
+    Tag::head, Tag::hhea, Tag::loca, Tag::maxp, Tag::cvt,
+    Tag::prep, Tag::glyf, Tag::hmtx, Tag::fpgm, Tag::EBDT,
+    Tag::EBLC, Tag::EBSC, Tag::bdat, Tag::bloc, Tag::bhed,
+    Tag::cmap,  // Keep here for future tagged PDF development.
+    Tag::name,  // Keep here due to legal concerns: copyright info inside.
+  };
+
+  // Setup font builders we need.
+  FontBuilderPtr font_builder;
+  font_builder.Attach(factory_->NewFontBuilder());
+  IntegerSet remove_tags;
+
+  if (SetupGlyfBuilders(font_builder, glyf, loca, glyph_ids)) {
+    remove_tags.insert(Tag::glyf);
+    remove_tags.insert(Tag::loca);
+  }
+
+  // For old Apple bitmap fonts, they have only bdats and bhed is identical
+  // to head.  As a result, we can't remove bdat tables for those fonts.
+  int setup_result = SetupBitmapBuilders(font_, font_builder, glyph_ids);
+  if (setup_result == kRemoveBDATAndEBDT || setup_result == kRemoveEBDT) {
+    remove_tags.insert(Tag::EBDT);
+    remove_tags.insert(Tag::EBLC);
+    remove_tags.insert(Tag::EBSC);
+  }
+
+  if (setup_result == kRemoveBDAT || setup_result == kRemoveBDATAndEBDT) {
+    remove_tags.insert(Tag::bdat);
+    remove_tags.insert(Tag::bloc);
+    remove_tags.insert(Tag::bhed);
+  }
+
+  IntegerSet allowed_tags;
+  for (size_t i = 0; i < sizeof(TABLES_IN_SUBSET) / sizeof(int32_t); ++i) {
+    allowed_tags.insert(TABLES_IN_SUBSET[i]);
+  }
+
+  IntegerSet result;
+  std::set_difference(allowed_tags.begin(), allowed_tags.end(),
+                      remove_tags.begin(), remove_tags.end(),
+                      std::inserter(result, result.end()));
+  allowed_tags = result;
+
+  // Setup remaining builders.
+  for (IntegerSet::iterator i = allowed_tags.begin(), e = allowed_tags.end();
+                            i != e; ++i) {
+    Table* table = font_->GetTable(*i);
+    if (table) {
+      font_builder->NewTableBuilder(*i, table->ReadFontData());
+    }
+  }
+
+  return font_builder->Build();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sample/chromium/subsetter_impl.h b/sfntly/cpp/src/sample/chromium/subsetter_impl.h
new file mode 100644
index 0000000..ffbf408
--- /dev/null
+++ b/sfntly/cpp/src/sample/chromium/subsetter_impl.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+// File is originally from Chromium third_party/sfntly/src/subsetter.
+// Use as test case in sfntly so that problems can be caught in upstream early.
+
+#ifndef SFNTLY_CPP_SRC_TEST_SUBSETTER_IMPL_H_
+#define SFNTLY_CPP_SRC_TEST_SUBSETTER_IMPL_H_
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/truetype/glyph_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+#include "sfntly/tag.h"
+
+namespace sfntly {
+
+// Smart pointer usage in sfntly:
+//
+// sfntly carries a smart pointer implementation like COM.  Ref-countable object
+// type inherits from RefCounted<>, which have AddRef and Release just like
+// IUnknown (but no QueryInterface).  Use a Ptr<> based smart pointer to hold
+// the object so that the object ref count is handled correctly.
+//
+// class Foo : public RefCounted<Foo> {
+//  public:
+//   static Foo* CreateInstance() {
+//     Ptr<Foo> obj = new Foo();  // ref count = 1
+//     return obj.detach();
+//   }
+// };
+// typedef Ptr<Foo> FooPtr;  // common short-hand notation
+// FooPtr obj;
+// obj.attach(Foo::CreatedInstance());  // ref count = 1
+// {
+//   FooPtr obj2 = obj;  // ref count = 2
+// }  // ref count = 1, obj2 out of scope
+// obj.release();  // ref count = 0, object destroyed
+
+class SubsetterImpl {
+ public:
+  SubsetterImpl();
+  ~SubsetterImpl();
+
+  bool LoadFont(const char* font_name,
+                const unsigned char* original_font,
+                size_t font_size);
+  int SubsetFont(const unsigned int* glyph_ids,
+                 size_t glyph_count,
+                 unsigned char** output_buffer);
+
+ private:
+  CALLER_ATTACH Font* Subset(const IntegerSet& glyph_ids,
+                             GlyphTable* glyf, LocaTable* loca);
+
+  FontFactoryPtr factory_;
+  FontPtr font_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_TEST_SUBSETTER_IMPL_H_
diff --git a/sfntly/cpp/src/sample/subsetter/main.cc b/sfntly/cpp/src/sample/subsetter/main.cc
new file mode 100644
index 0000000..19a3e0e
--- /dev/null
+++ b/sfntly/cpp/src/sample/subsetter/main.cc
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+#if _MSC_VER > 12
+  #define _CRTDBG_MAP_ALLOC
+  #include <stdlib.h>
+  #include <crtdbg.h>
+#endif
+
+#include "sample/subsetter/subset_util.h"
+
+int main(int argc, char** argv) {
+#ifdef _CRTDBG_MAP_ALLOC
+  _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF);
+#endif
+
+  if (argc < 3) {
+    printf("Usage: subsetter <font file> <output file>\n");
+    return 0;
+  }
+
+  sfntly::SubsetUtil subset_util;
+  subset_util.Subset(argv[1], argv[2]);
+
+#ifdef _CRTDBG_MAP_ALLOC
+  _CrtDumpMemoryLeaks();
+#endif
+
+  return 0;
+}
diff --git a/sfntly/cpp/src/sample/subsetter/subset_util.cc b/sfntly/cpp/src/sample/subsetter/subset_util.cc
new file mode 100644
index 0000000..f35eb25
--- /dev/null
+++ b/sfntly/cpp/src/sample/subsetter/subset_util.cc
@@ -0,0 +1,98 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// Remove VC++ nag on fopen.
+#define _CRT_SECURE_NO_WARNINGS
+
+#include "sample/subsetter/subset_util.h"
+
+#include <stdio.h>
+
+#include <vector>
+#include <memory>
+
+#include "sfntly/font.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "sfntly/port/type.h"
+#include "sfntly/tag.h"
+#include "sfntly/tools/subsetter/subsetter.h"
+
+namespace sfntly {
+
+SubsetUtil::SubsetUtil() {
+}
+
+SubsetUtil::~SubsetUtil() {
+}
+
+void SubsetUtil::Subset(const char *input_file_path,
+                        const char *output_file_path) {
+  UNREFERENCED_PARAMETER(output_file_path);
+  ByteVector input_buffer;
+  FILE* input_file = fopen(input_file_path, "rb");
+  if (input_file == NULL) {
+    fprintf(stderr, "file not found\n");
+    return;
+  }
+  fseek(input_file, 0, SEEK_END);
+  size_t file_size = ftell(input_file);
+  fseek(input_file, 0, SEEK_SET);
+  input_buffer.resize(file_size);
+  size_t bytes_read = fread(&(input_buffer[0]), 1, file_size, input_file);
+  UNREFERENCED_PARAMETER(bytes_read);
+  fclose(input_file);
+
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+
+  FontArray font_array;
+  factory->LoadFonts(&input_buffer, &font_array);
+  if (font_array.empty() || font_array[0] == NULL)
+    return;
+
+  IntegerList glyphs;
+  for (int32_t i = 0; i < 10; i++) {
+    glyphs.push_back(i);
+  }
+  glyphs.push_back(11);
+  glyphs.push_back(10);
+
+  Ptr<Subsetter> subsetter = new Subsetter(font_array[0], factory);
+  subsetter->SetGlyphs(&glyphs);
+  IntegerSet remove_tables;
+  remove_tables.insert(Tag::DSIG);
+  subsetter->SetRemoveTables(&remove_tables);
+
+  FontBuilderPtr font_builder;
+  font_builder.Attach(subsetter->Subset());
+
+  FontPtr new_font;
+  new_font.Attach(font_builder->Build());
+
+  // TODO(arthurhsu): glyph renumbering/Loca table
+  // TODO(arthurhsu): alter CMaps
+
+  MemoryOutputStream output_stream;
+  factory->SerializeFont(new_font, &output_stream);
+
+  FILE* output_file = fopen(output_file_path, "wb");
+  fwrite(output_stream.Get(), 1, output_stream.Size(), output_file);
+  fflush(output_file);
+  fclose(output_file);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sample/subsetter/subset_util.h b/sfntly/cpp/src/sample/subsetter/subset_util.h
new file mode 100644
index 0000000..5eb4fe4
--- /dev/null
+++ b/sfntly/cpp/src/sample/subsetter/subset_util.h
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SAMPLE_SUBSETTER_SUBSET_UTIL_H_
+#define SFNTLY_CPP_SRC_SAMPLE_SUBSETTER_SUBSET_UTIL_H_
+
+namespace sfntly {
+
+class SubsetUtil {
+ public:
+  SubsetUtil();
+  virtual ~SubsetUtil();
+
+  void Subset(const char* input_file_path, const char* output_file_path);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SAMPLE_SUBSETTER_SUBSET_UTIL_H_
diff --git a/sfntly/cpp/src/sample/subtly/character_predicate.cc b/sfntly/cpp/src/sample/subtly/character_predicate.cc
new file mode 100644
index 0000000..b9c6cc7
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/character_predicate.cc
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/port/refcount.h"
+#include "subtly/character_predicate.h"
+
+namespace subtly {
+using namespace sfntly;
+
+// AcceptRange predicate
+AcceptRange::AcceptRange(int32_t start, int32_t end)
+    : start_(start),
+      end_(end) {
+}
+
+AcceptRange::~AcceptRange() {}
+
+bool AcceptRange::operator()(int32_t character) const {
+  return start_ <= character && character <= end_;
+}
+
+// AcceptSet predicate
+AcceptSet::AcceptSet(IntegerSet* characters)
+    : characters_(characters) {
+}
+
+AcceptSet::~AcceptSet() {
+  delete characters_;
+}
+
+bool AcceptSet::operator()(int32_t character) const {
+  return characters_->find(character) != characters_->end();
+}
+
+// AcceptAll predicate
+bool AcceptAll::operator()(int32_t character) const {
+  UNREFERENCED_PARAMETER(character);
+  return true;
+}
+}
diff --git a/sfntly/cpp/src/sample/subtly/character_predicate.h b/sfntly/cpp/src/sample/subtly/character_predicate.h
new file mode 100644
index 0000000..a6e3ea3
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/character_predicate.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_CHARACTER_PREDICATE_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_CHARACTER_PREDICATE_H_
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/port/type.h"
+
+namespace subtly {
+class CharacterPredicate : virtual public sfntly::RefCount {
+ public:
+  CharacterPredicate() {}
+  virtual ~CharacterPredicate() {}
+  virtual bool operator()(int32_t character) const = 0;
+};
+
+// All characters except for those between [start, end] are rejected
+class AcceptRange : public CharacterPredicate,
+                    public sfntly::RefCounted<AcceptRange> {
+ public:
+  AcceptRange(int32_t start, int32_t end);
+  ~AcceptRange();
+  virtual bool operator()(int32_t character) const;
+
+ private:
+  int32_t start_;
+  int32_t end_;
+};
+
+// All characters in IntegerSet
+// The set is OWNED by the predicate! Do not modify it.
+// It will be freed when the predicate is destroyed.
+class AcceptSet : public CharacterPredicate,
+                  public sfntly::RefCounted<AcceptSet> {
+ public:
+  explicit AcceptSet(sfntly::IntegerSet* characters);
+  ~AcceptSet();
+  virtual bool operator()(int32_t character) const;
+
+ private:
+  sfntly::IntegerSet* characters_;
+};
+
+// All characters
+class AcceptAll : public CharacterPredicate,
+                  public sfntly::RefCounted<AcceptAll> {
+ public:
+  AcceptAll() {}
+  ~AcceptAll() {}
+  virtual bool operator()(int32_t character) const;
+};
+}
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_CHARACTER_PREDICATE_H_
diff --git a/sfntly/cpp/src/sample/subtly/debug_main.cc b/sfntly/cpp/src/sample/subtly/debug_main.cc
new file mode 100644
index 0000000..8324cde
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/debug_main.cc
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <map>
+#include <utility>
+
+#include "sfntly/font.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/tag.h"
+#include "subtly/stats.h"
+#include "subtly/subsetter.h"
+#include "subtly/utils.h"
+
+using namespace subtly;
+
+void PrintUsage(const char* program_name) {
+  fprintf(stdout, "Usage: %s <input_font_file>\n", program_name);
+}
+
+int main(int argc, const char** argv) {
+  const char* program_name = argv[0];
+  if (argc < 2) {
+    PrintUsage(program_name);
+    exit(1);
+  }
+
+  const char* input_font_path = argv[1];
+  const char* output_font_path = argv[2];
+  FontPtr font;
+  font.Attach(subtly::LoadFont(input_font_path));
+
+  int32_t original_size = TotalFontSize(font);
+  Ptr<Subsetter> subsetter = new Subsetter(font, NULL);
+  Ptr<Font> new_font;
+  new_font.Attach(subsetter->Subset());
+  if (!new_font) {
+    fprintf(stdout, "Cannot create subset.\n");
+    return 0;
+  }
+
+  subtly::SerializeFont(output_font_path, new_font);
+  subtly::PrintComparison(stdout, font, new_font);
+  int32_t new_size = TotalFontSize(new_font);
+  fprintf(stdout, "Went from %d to %d: %lf%% of original\n",
+          original_size, new_size,
+          static_cast<double>(new_size) / original_size * 100);
+  return 0;
+}
diff --git a/sfntly/cpp/src/sample/subtly/font_assembler.cc b/sfntly/cpp/src/sample/subtly/font_assembler.cc
new file mode 100644
index 0000000..2f7cd11
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/font_assembler.cc
@@ -0,0 +1,227 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "subtly/font_assembler.h"
+
+#include <stdio.h>
+
+#include <set>
+#include <map>
+
+#include "sfntly/tag.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+#include "sfntly/table/truetype/glyph_table.h"
+#include "sfntly/table/core/maximum_profile_table.h"
+#include "sfntly/port/type.h"
+#include "sfntly/port/refcount.h"
+#include "subtly/font_info.h"
+
+namespace subtly {
+using namespace sfntly;
+
+FontAssembler::FontAssembler(FontInfo* font_info,
+                             IntegerSet* table_blacklist)
+    : table_blacklist_(table_blacklist) {
+  font_info_ = font_info;
+  Initialize();
+}
+
+FontAssembler::FontAssembler(FontInfo* font_info)
+    : table_blacklist_(NULL) {
+  font_info_ = font_info;
+  Initialize();
+}
+
+void FontAssembler::Initialize() {
+  font_factory_.Attach(sfntly::FontFactory::GetInstance());
+  font_builder_.Attach(font_factory_->NewFontBuilder());
+}
+
+CALLER_ATTACH Font* FontAssembler::Assemble() {
+  // Assemble tables we can subset.
+  if (!AssembleCMapTable() || !AssembleGlyphAndLocaTables()) {
+    return NULL;
+  }
+  // For all other tables, either include them unmodified or don't at all.
+  const TableMap* common_table_map =
+      font_info_->GetTableMap(font_info_->fonts()->begin()->first);
+  for (TableMap::const_iterator it = common_table_map->begin(),
+           e = common_table_map->end(); it != e; ++it) {
+    if (table_blacklist_
+        && table_blacklist_->find(it->first) != table_blacklist_->end()) {
+      continue;
+    }
+    font_builder_->NewTableBuilder(it->first, it->second->ReadFontData());
+  }
+  return font_builder_->Build();
+}
+
+bool FontAssembler::AssembleCMapTable() {
+  // Creating the new CMapTable and the new format 4 CMap
+  Ptr<CMapTable::Builder> cmap_table_builder =
+      down_cast<CMapTable::Builder*>
+      (font_builder_->NewTableBuilder(Tag::cmap));
+  if (!cmap_table_builder)
+    return false;
+  Ptr<CMapTable::CMapFormat4::Builder> cmap_builder =
+      down_cast<CMapTable::CMapFormat4::Builder*>
+      (cmap_table_builder->NewCMapBuilder(CMapFormat::kFormat4,
+                                          CMapTable::WINDOWS_BMP));
+  if (!cmap_builder)
+    return false;
+  // Creating the segments and the glyph id array
+  CharacterMap* chars_to_glyph_ids = font_info_->chars_to_glyph_ids();
+  SegmentList* segment_list = new SegmentList;
+  IntegerList* glyph_id_array = new IntegerList;
+  int32_t last_chararacter = -2;
+  int32_t last_offset = 0;
+  Ptr<CMapTable::CMapFormat4::Builder::Segment> current_segment;
+
+  // For simplicity, we will have one segment per contiguous range.
+  // To test the algorithm, we've replaced the original CMap with the CMap
+  // generated by this code without removing any character.
+  // Tuffy.ttf: CMap went from 3146 to 3972 bytes (1.7% to 2.17% of file)
+  // AnonymousPro.ttf: CMap went from 1524 to 1900 bytes (0.96% to 1.2%)
+  for (CharacterMap::iterator it = chars_to_glyph_ids->begin(),
+           e = chars_to_glyph_ids->end(); it != e; ++it) {
+    int32_t character = it->first;
+    int32_t glyph_id = it->second.glyph_id();
+    if (character != last_chararacter + 1) {  // new segment
+      if (current_segment != NULL) {
+        current_segment->set_end_count(last_chararacter);
+        segment_list->push_back(current_segment);
+      }
+      // start_code = character
+      // end_code = -1 (unknown for now)
+      // id_delta = 0 (we don't use id_delta for this representation)
+      // id_range_offset = last_offset (offset into the glyph_id_array)
+      current_segment =
+          new CMapTable::CMapFormat4::Builder::
+          Segment(character, -1, 0, last_offset);
+    }
+    glyph_id_array->push_back(glyph_id);
+    last_offset += DataSize::kSHORT;
+    last_chararacter = character;
+  }
+  // The last segment is still open.
+  current_segment->set_end_count(last_chararacter);
+  segment_list->push_back(current_segment);
+  // Updating the id_range_offset for every segment.
+  for (int32_t i = 0, num_segs = segment_list->size(); i < num_segs; ++i) {
+    Ptr<CMapTable::CMapFormat4::Builder::Segment> segment = segment_list->at(i);
+    segment->set_id_range_offset(segment->id_range_offset()
+                                 + (num_segs - i + 1) * DataSize::kSHORT);
+  }
+  // Adding the final, required segment.
+  current_segment =
+      new CMapTable::CMapFormat4::Builder::Segment(0xffff, 0xffff, 1, 0);
+  segment_list->push_back(current_segment);
+  // Writing the segments and glyph id array to the CMap
+  cmap_builder->set_segments(segment_list);
+  cmap_builder->set_glyph_id_array(glyph_id_array);
+  delete segment_list;
+  delete glyph_id_array;
+  return true;
+}
+
+bool FontAssembler::AssembleGlyphAndLocaTables() {
+  Ptr<LocaTable::Builder> loca_table_builder =
+      down_cast<LocaTable::Builder*>
+      (font_builder_->NewTableBuilder(Tag::loca));
+  Ptr<GlyphTable::Builder> glyph_table_builder =
+      down_cast<GlyphTable::Builder*>
+      (font_builder_->NewTableBuilder(Tag::glyf));
+
+  GlyphIdSet* resolved_glyph_ids = font_info_->resolved_glyph_ids();
+  IntegerList loca_list;
+  // Basic sanity check: all LOCA tables are of the same size
+  // This is necessary but not suficient!
+  int32_t previous_size = -1;
+  for (FontIdMap::iterator it = font_info_->fonts()->begin();
+       it != font_info_->fonts()->end(); ++it) {
+    Ptr<LocaTable> loca_table =
+        down_cast<LocaTable*>(font_info_->GetTable(it->first, Tag::loca));
+    int32_t current_size = loca_table->header_length();
+    if (previous_size != -1 && current_size != previous_size) {
+      return false;
+    }
+    previous_size = current_size;
+  }
+
+  // Assuming all fonts referenced by the FontInfo are the subsets of the same
+  // font, their loca tables should all have the same sizes.
+  // We'll just get the size of the first font's LOCA table for simplicty.
+  Ptr<LocaTable> first_loca_table =
+    down_cast<LocaTable*>
+    (font_info_->GetTable(font_info_->fonts()->begin()->first, Tag::loca));
+  int32_t num_loca_glyphs = first_loca_table->num_glyphs();
+  loca_list.resize(num_loca_glyphs);
+  loca_list.push_back(0);
+  int32_t last_glyph_id = 0;
+  int32_t last_offset = 0;
+  GlyphTable::GlyphBuilderList* glyph_builders =
+      glyph_table_builder->GlyphBuilders();
+
+  for (GlyphIdSet::iterator it = resolved_glyph_ids->begin(),
+           e = resolved_glyph_ids->end(); it != e; ++it) {
+    // Get the glyph for this resolved_glyph_id.
+    int32_t resolved_glyph_id = it->glyph_id();
+    int32_t font_id = it->font_id();
+    // Get the LOCA table for the current glyph id.
+    Ptr<LocaTable> loca_table =
+        down_cast<LocaTable*>
+        (font_info_->GetTable(font_id, Tag::loca));
+    int32_t length = loca_table->GlyphLength(resolved_glyph_id);
+    int32_t offset = loca_table->GlyphOffset(resolved_glyph_id);
+
+    // Get the GLYF table for the current glyph id.
+    Ptr<GlyphTable> glyph_table =
+        down_cast<GlyphTable*>
+        (font_info_->GetTable(font_id, Tag::glyf));
+    GlyphPtr glyph;
+    glyph.Attach(glyph_table->GetGlyph(offset, length));
+
+    // The data reference by the glyph is copied into a new glyph and
+    // added to the glyph_builders belonging to the glyph_table_builder.
+    // When Build gets called, all the glyphs will be built.
+    Ptr<ReadableFontData> data = glyph->ReadFontData();
+    Ptr<WritableFontData> copy_data;
+    copy_data.Attach(WritableFontData::CreateWritableFontData(data->Length()));
+    data->CopyTo(copy_data);
+    GlyphBuilderPtr glyph_builder;
+    glyph_builder.Attach(glyph_table_builder->GlyphBuilder(copy_data));
+    glyph_builders->push_back(glyph_builder);
+
+    // If there are missing glyphs between the last glyph_id and the
+    // current resolved_glyph_id, since the LOCA table needs to have the same
+    // size, the offset is kept the same.
+    for (int32_t i = last_glyph_id + 1; i <= resolved_glyph_id; ++i)
+      loca_list[i] = last_offset;
+    last_offset += length;
+    loca_list[resolved_glyph_id + 1] = last_offset;
+    last_glyph_id = resolved_glyph_id + 1;
+  }
+  // If there are missing glyph ids, their loca entries must all point
+  // to the same offset as the last valid glyph id making them all zero length.
+  for (int32_t i = last_glyph_id + 1; i <= num_loca_glyphs; ++i)
+    loca_list[i] = last_offset;
+  loca_table_builder->SetLocaList(&loca_list);
+  return true;
+}
+}
diff --git a/sfntly/cpp/src/sample/subtly/font_assembler.h b/sfntly/cpp/src/sample/subtly/font_assembler.h
new file mode 100644
index 0000000..c53c21f
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/font_assembler.h
@@ -0,0 +1,67 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_FONT_ASSEMBLER_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_FONT_ASSEMBLER_H_
+
+#include <set>
+#include <map>
+
+#include "subtly/font_info.h"
+
+#include "sfntly/tag.h"
+#include "sfntly/font.h"
+#include "sfntly/port/type.h"
+#include "sfntly/port/refcount.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/table/truetype/glyph_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+
+namespace subtly {
+// Assembles FontInfo into font builders.
+// Does not take ownership of data passed to it.
+class FontAssembler : public sfntly::RefCounted<FontAssembler> {
+ public:
+  // font_info is the FontInfo which will be used for the new font
+  // table_blacklist is used to decide which tables to exclude from the
+  // final font.
+  FontAssembler(FontInfo* font_info, sfntly::IntegerSet* table_blacklist);
+  explicit FontAssembler(FontInfo* font_info);
+  ~FontAssembler() { }
+
+  // Assemble a new font from the font info object.
+  virtual CALLER_ATTACH sfntly::Font* Assemble();
+
+  sfntly::IntegerSet* table_blacklist() const { return table_blacklist_; }
+  void set_table_blacklist(sfntly::IntegerSet* table_blacklist) {
+    table_blacklist_ = table_blacklist;
+  }
+
+ protected:
+  virtual bool AssembleCMapTable();
+  virtual bool AssembleGlyphAndLocaTables();
+
+  virtual void Initialize();
+
+ private:
+  sfntly::Ptr<FontInfo> font_info_;
+  sfntly::Ptr<sfntly::FontFactory> font_factory_;
+  sfntly::Ptr<sfntly::Font::Builder> font_builder_;
+  sfntly::IntegerSet* table_blacklist_;
+};
+}
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_FONT_ASSEMBLER_H_
diff --git a/sfntly/cpp/src/sample/subtly/font_info.cc b/sfntly/cpp/src/sample/subtly/font_info.cc
new file mode 100644
index 0000000..6eb6a38
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/font_info.cc
@@ -0,0 +1,256 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "subtly/font_info.h"
+
+#include <stdio.h>
+
+#include <set>
+#include <map>
+
+#include "subtly/character_predicate.h"
+
+#include "sfntly/tag.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+#include "sfntly/table/truetype/glyph_table.h"
+#include "sfntly/table/core/maximum_profile_table.h"
+#include "sfntly/port/type.h"
+#include "sfntly/port/refcount.h"
+
+namespace subtly {
+using namespace sfntly;
+/******************************************************************************
+ * GlyphId class
+ ******************************************************************************/
+GlyphId::GlyphId(int32_t glyph_id, FontId font_id)
+    : glyph_id_(glyph_id),
+      font_id_(font_id) {
+}
+
+bool GlyphId::operator==(const GlyphId& other) const {
+  return glyph_id_ == other.glyph_id();
+}
+
+bool GlyphId::operator<(const GlyphId& other) const {
+  return glyph_id_ < other.glyph_id();
+}
+
+/******************************************************************************
+ * FontInfo class
+ ******************************************************************************/
+FontInfo::FontInfo()
+    : chars_to_glyph_ids_(new CharacterMap),
+      resolved_glyph_ids_(new GlyphIdSet),
+      fonts_(new FontIdMap) {
+}
+
+FontInfo::FontInfo(CharacterMap* chars_to_glyph_ids,
+                   GlyphIdSet* resolved_glyph_ids,
+                   FontIdMap* fonts) {
+  chars_to_glyph_ids_ = new CharacterMap(chars_to_glyph_ids->begin(),
+                                         chars_to_glyph_ids->end());
+  resolved_glyph_ids_ = new GlyphIdSet(resolved_glyph_ids->begin(),
+                                       resolved_glyph_ids->end());
+  fonts_ = new FontIdMap(fonts->begin(), fonts->end());
+}
+
+FontInfo::~FontInfo() {
+  delete chars_to_glyph_ids_;
+  delete resolved_glyph_ids_;
+  delete fonts_;
+}
+
+FontDataTable* FontInfo::GetTable(FontId font_id, int32_t tag) {
+  if (!fonts_)
+    return NULL;
+  FontIdMap::iterator it = fonts_->find(font_id);
+  if (it == fonts_->end())
+    return NULL;
+  return it->second->GetTable(tag);
+}
+
+const TableMap* FontInfo::GetTableMap(FontId font_id) {
+  if (!fonts_)
+    return NULL;
+  FontIdMap::iterator it = fonts_->find(font_id);
+  if (it == fonts_->end())
+    return NULL;
+  return it->second->GetTableMap();
+}
+
+void FontInfo::set_chars_to_glyph_ids(CharacterMap* chars_to_glyph_ids) {
+  *chars_to_glyph_ids_ = *chars_to_glyph_ids;
+}
+
+void FontInfo::set_resolved_glyph_ids(GlyphIdSet* resolved_glyph_ids) {
+  *resolved_glyph_ids_ = *resolved_glyph_ids;
+}
+
+void FontInfo::set_fonts(FontIdMap* fonts) {
+  *fonts_ = *fonts;
+}
+
+/******************************************************************************
+ * FontSourcedInfoBuilder class
+ ******************************************************************************/
+FontSourcedInfoBuilder::FontSourcedInfoBuilder(Font* font, FontId font_id)
+    : font_(font),
+      font_id_(font_id),
+      predicate_(NULL) {
+  Initialize();
+}
+
+FontSourcedInfoBuilder::FontSourcedInfoBuilder(Font* font,
+                                               FontId font_id,
+                                               CharacterPredicate* predicate)
+    : font_(font),
+      font_id_(font_id),
+      predicate_(predicate) {
+  Initialize();
+}
+
+void FontSourcedInfoBuilder::Initialize() {
+  Ptr<CMapTable> cmap_table = down_cast<CMapTable*>(font_->GetTable(Tag::cmap));
+  // We prefer Windows BMP format 4 cmaps.
+  cmap_.Attach(cmap_table->GetCMap(CMapTable::WINDOWS_BMP));
+  // But if none is found,
+  if (!cmap_) {
+    return;
+  }
+  loca_table_ = down_cast<LocaTable*>(font_->GetTable(Tag::loca));
+  glyph_table_ = down_cast<GlyphTable*>(font_->GetTable(Tag::glyf));
+}
+
+CALLER_ATTACH FontInfo* FontSourcedInfoBuilder::GetFontInfo() {
+  CharacterMap* chars_to_glyph_ids = new CharacterMap;
+  bool success = GetCharacterMap(chars_to_glyph_ids);
+  if (!success) {
+    delete chars_to_glyph_ids;
+#if defined (SUBTLY_DEBUG)
+    fprintf(stderr, "Error creating character map.\n");
+#endif
+    return NULL;
+  }
+  GlyphIdSet* resolved_glyph_ids = new GlyphIdSet;
+  success = ResolveCompositeGlyphs(chars_to_glyph_ids, resolved_glyph_ids);
+  if (!success) {
+    delete chars_to_glyph_ids;
+    delete resolved_glyph_ids;
+#if defined (SUBTLY_DEBUG)
+    fprintf(stderr, "Error resolving composite glyphs.\n");
+#endif
+    return NULL;
+  }
+  Ptr<FontInfo> font_info = new FontInfo;
+  font_info->set_chars_to_glyph_ids(chars_to_glyph_ids);
+  font_info->set_resolved_glyph_ids(resolved_glyph_ids);
+  FontIdMap* font_id_map = new FontIdMap;
+  font_id_map->insert(std::make_pair(font_id_, font_));
+  font_info->set_fonts(font_id_map);
+  delete chars_to_glyph_ids;
+  delete resolved_glyph_ids;
+  delete font_id_map;
+  return font_info.Detach();
+}
+
+bool FontSourcedInfoBuilder::GetCharacterMap(CharacterMap* chars_to_glyph_ids) {
+  if (!cmap_ || !chars_to_glyph_ids)
+    return false;
+  chars_to_glyph_ids->clear();
+  CMapTable::CMap::CharacterIterator* character_iterator = cmap_->Iterator();
+  if (!character_iterator)
+    return false;
+  while (character_iterator->HasNext()) {
+    int32_t character = character_iterator->Next();
+    if (!predicate_ || (*predicate_)(character)) {
+      chars_to_glyph_ids->insert
+          (std::make_pair(character,
+                          GlyphId(cmap_->GlyphId(character), font_id_)));
+    }
+  }
+  delete character_iterator;
+  return true;
+}
+
+bool
+FontSourcedInfoBuilder::ResolveCompositeGlyphs(CharacterMap* chars_to_glyph_ids,
+                                               GlyphIdSet* resolved_glyph_ids) {
+  if (!chars_to_glyph_ids || !resolved_glyph_ids)
+    return false;
+  resolved_glyph_ids->clear();
+  resolved_glyph_ids->insert(GlyphId(0, font_id_));
+  IntegerSet* unresolved_glyph_ids = new IntegerSet;
+  // Since composite glyph elements might themselves be composite, we would need
+  // to recursively resolve the elements too. To avoid the recursion we
+  // create two sets, |unresolved_glyph_ids| for the unresolved glyphs,
+  // initially containing all the ids and |resolved_glyph_ids|, initially empty.
+  // We'll remove glyph ids from |unresolved_glyph_ids| until it is empty and,
+  // if the glyph is composite, add its elements to the unresolved set.
+  for (CharacterMap::iterator it = chars_to_glyph_ids->begin(),
+           e = chars_to_glyph_ids->end(); it != e; ++it) {
+    unresolved_glyph_ids->insert(it->second.glyph_id());
+  }
+  // As long as there are unresolved glyph ids.
+  while (!unresolved_glyph_ids->empty()) {
+    // Get the corresponding glyph.
+    int32_t glyph_id = *(unresolved_glyph_ids->begin());
+    unresolved_glyph_ids->erase(unresolved_glyph_ids->begin());
+    if (glyph_id < 0 || glyph_id > loca_table_->num_glyphs()) {
+#if defined (SUBTLY_DEBUG)
+      fprintf(stderr, "%d larger than %d or smaller than 0\n", glyph_id,
+              loca_table_->num_glyphs());
+#endif
+      continue;
+    }
+    int32_t length = loca_table_->GlyphLength(glyph_id);
+    if (length == 0) {
+#if defined (SUBTLY_DEBUG)
+      fprintf(stderr, "Zero length glyph %d\n", glyph_id);
+#endif
+      continue;
+    }
+    int32_t offset = loca_table_->GlyphOffset(glyph_id);
+    GlyphPtr glyph;
+    glyph.Attach(glyph_table_->GetGlyph(offset, length));
+    if (glyph == NULL) {
+#if defined (SUBTLY_DEBUG)
+      fprintf(stderr, "GetGlyph returned NULL for %d\n", glyph_id);
+#endif
+      continue;
+    }
+    // Mark the glyph as resolved.
+    resolved_glyph_ids->insert(GlyphId(glyph_id, font_id_));
+    // If it is composite, add all its components to the unresolved glyph set.
+    if (glyph->GlyphType() == GlyphType::kComposite) {
+      Ptr<GlyphTable::CompositeGlyph> composite_glyph =
+          down_cast<GlyphTable::CompositeGlyph*>(glyph.p_);
+      int32_t num_glyphs = composite_glyph->NumGlyphs();
+      for (int32_t i = 0; i < num_glyphs; ++i) {
+        int32_t glyph_id = composite_glyph->GlyphIndex(i);
+        if (resolved_glyph_ids->find(GlyphId(glyph_id, -1))
+            == resolved_glyph_ids->end()) {
+          unresolved_glyph_ids->insert(glyph_id);
+        }
+      }
+    }
+  }
+  delete unresolved_glyph_ids;
+  return true;
+}
+}
diff --git a/sfntly/cpp/src/sample/subtly/font_info.h b/sfntly/cpp/src/sample/subtly/font_info.h
new file mode 100644
index 0000000..6f42d73
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/font_info.h
@@ -0,0 +1,128 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_FONT_INFO_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_FONT_INFO_H_
+
+#include <map>
+#include <set>
+
+#include "sfntly/font.h"
+#include "sfntly/port/type.h"
+#include "sfntly/port/refcount.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/table/truetype/glyph_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+
+namespace subtly {
+class CharacterPredicate;
+
+typedef int32_t FontId;
+typedef std::map<FontId, sfntly::Ptr<sfntly::Font> > FontIdMap;
+
+// Glyph id pair that contains the loca table glyph id as well as the
+// font id that has the glyph table this glyph belongs to.
+class GlyphId {
+ public:
+  GlyphId(int32_t glyph_id, FontId font_id);
+  ~GlyphId() {}
+
+  bool operator==(const GlyphId& other) const;
+  bool operator<(const GlyphId& other) const;
+
+  int32_t glyph_id() const { return glyph_id_; }
+  void set_glyph_id(const int32_t glyph_id) { glyph_id_ = glyph_id; }
+  FontId font_id() const { return font_id_; }
+  void set_font_id(const FontId font_id) { font_id_ = font_id; }
+
+ private:
+  int32_t glyph_id_;
+  FontId font_id_;
+};
+
+typedef std::map<int32_t, GlyphId> CharacterMap;
+typedef std::set<GlyphId> GlyphIdSet;
+
+// Font information used for FontAssembler in the construction of a new font.
+// Will make copies of character map, glyph id set and font id map.
+class FontInfo : public sfntly::RefCounted<FontInfo> {
+ public:
+  // Empty FontInfo object.
+  FontInfo();
+  // chars_to_glyph_ids maps characters to GlyphIds for CMap construction
+  // resolved_glyph_ids defines GlyphIds which should be in the final font
+  // fonts is a map of font ids to fonts to reference any needed table
+  FontInfo(CharacterMap* chars_to_glyph_ids,
+           GlyphIdSet* resolved_glyph_ids,
+           FontIdMap* fonts);
+  virtual ~FontInfo();
+
+  // Gets the table with the specified tag from the font corresponding to
+  // font_id or NULL if there is no such font/table.
+  // font_id is the id of the font that contains the table
+  // tag identifies the table to be obtained
+  virtual sfntly::FontDataTable* GetTable(FontId font_id, int32_t tag);
+  // Gets the table map of the font whose id is font_id
+  virtual const sfntly::TableMap* GetTableMap(FontId);
+
+  CharacterMap* chars_to_glyph_ids() const { return chars_to_glyph_ids_; }
+  // Takes ownership of the chars_to_glyph_ids CharacterMap.
+  void set_chars_to_glyph_ids(CharacterMap* chars_to_glyph_ids);
+  GlyphIdSet* resolved_glyph_ids() const { return resolved_glyph_ids_; }
+  // Takes ownership of the glyph_ids GlyphIdSet.
+  void set_resolved_glyph_ids(GlyphIdSet* glyph_ids);
+  FontIdMap* fonts() const { return fonts_; }
+  // Takes ownership of the fonts FontIdMap.
+  void set_fonts(FontIdMap* fonts);
+
+ private:
+  CharacterMap* chars_to_glyph_ids_;
+  GlyphIdSet* resolved_glyph_ids_;
+  FontIdMap* fonts_;
+};
+
+// FontSourcedInfoBuilder is used to create a FontInfo object from a Font
+// optionally specifying a CharacterPredicate to filter out some of
+// the font's characters.
+// It does not take ownership or copy the values its constructor receives.
+class FontSourcedInfoBuilder :
+      public sfntly::RefCounted<FontSourcedInfoBuilder> {
+ public:
+  FontSourcedInfoBuilder(sfntly::Font* font, FontId font_id);
+  FontSourcedInfoBuilder(sfntly::Font* font,
+                         FontId font_id,
+                         CharacterPredicate* predicate);
+  virtual ~FontSourcedInfoBuilder() { }
+
+  virtual CALLER_ATTACH FontInfo* GetFontInfo();
+
+ protected:
+  bool GetCharacterMap(CharacterMap* chars_to_glyph_ids);
+  bool ResolveCompositeGlyphs(CharacterMap* chars_to_glyph_ids,
+                              GlyphIdSet* resolved_glyph_ids);
+  void Initialize();
+
+ private:
+  sfntly::Ptr<sfntly::Font> font_;
+  FontId font_id_;
+  CharacterPredicate* predicate_;
+
+  sfntly::Ptr<sfntly::CMapTable::CMap> cmap_;
+  sfntly::Ptr<sfntly::LocaTable> loca_table_;
+  sfntly::Ptr<sfntly::GlyphTable> glyph_table_;
+};
+}
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_FONT_INFO_H_
diff --git a/sfntly/cpp/src/sample/subtly/merger.cc b/sfntly/cpp/src/sample/subtly/merger.cc
new file mode 100644
index 0000000..7875c2d
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/merger.cc
@@ -0,0 +1,87 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "subtly/merger.h"
+
+#include <stdio.h>
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "subtly/character_predicate.h"
+#include "subtly/font_assembler.h"
+#include "subtly/font_info.h"
+#include "subtly/utils.h"
+
+namespace subtly {
+using namespace sfntly;
+
+/******************************************************************************
+ * Merger class
+ ******************************************************************************/
+Merger::Merger(FontArray* fonts) {
+  if (!fonts) {
+    return;
+  }
+  int32_t num_fonts = fonts->size();
+  for (int32_t i = 0; i < num_fonts; ++i) {
+    fonts_.insert(std::make_pair(i, fonts->at(i)));
+  }
+}
+
+CALLER_ATTACH Font* Merger::Merge() {
+  Ptr<FontInfo> merged_info;
+  merged_info.Attach(MergeFontInfos());
+  if (!merged_info) {
+#if defined (SUBTLY_DEBUG)
+    fprintf(stderr, "Could not create merged font info\n");
+#endif
+    return NULL;
+  }
+  Ptr<FontAssembler> font_assembler = new FontAssembler(merged_info);
+  return font_assembler->Assemble();
+}
+
+CALLER_ATTACH FontInfo* Merger::MergeFontInfos() {
+  Ptr<FontInfo> font_info = new FontInfo;
+  font_info->set_fonts(&fonts_);
+  for (FontIdMap::iterator it = fonts_.begin(),
+           e = fonts_.end(); it != e; ++it) {
+    Ptr<FontSourcedInfoBuilder> info_builder =
+        new FontSourcedInfoBuilder(it->second, it->first, NULL);
+    Ptr<FontInfo> current_font_info;
+    current_font_info.Attach(info_builder->GetFontInfo());
+    if (!current_font_info) {
+#if defined (SUBTLY_DEBUG)
+      fprintf(stderr, "Couldn't create font info. "
+              "No subset will be generated.\n");
+#endif
+      return NULL;
+    }
+    font_info->chars_to_glyph_ids()->insert(
+        current_font_info->chars_to_glyph_ids()->begin(),
+        current_font_info->chars_to_glyph_ids()->end());
+    font_info->resolved_glyph_ids()->insert(
+        current_font_info->resolved_glyph_ids()->begin(),
+        current_font_info->resolved_glyph_ids()->end());
+#if defined (SUBTLY_DEBUG)
+    fprintf(stderr, "Counts: chars_to_glyph_ids: %d; resoved_glyph_ids: %d\n",
+            font_info->chars_to_glyph_ids()->size(),
+            font_info->resolved_glyph_ids()->size());
+#endif
+  }
+  return font_info.Detach();
+}
+}
diff --git a/sfntly/cpp/src/sample/subtly/merger.h b/sfntly/cpp/src/sample/subtly/merger.h
new file mode 100644
index 0000000..43764a8
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/merger.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_MERGER_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_MERGER_H_
+
+#include "subtly/character_predicate.h"
+#include "subtly/font_info.h"
+
+namespace sfntly {
+class Font;
+}
+
+namespace subtly {
+// Merges the subsets in the font array into a single font.
+class Merger : public sfntly::RefCounted<Merger> {
+ public:
+  explicit Merger(sfntly::FontArray* fonts);
+  virtual ~Merger() { }
+
+  // Performs merging returning the subsetted font.
+  virtual CALLER_ATTACH sfntly::Font* Merge();
+
+ protected:
+  virtual CALLER_ATTACH FontInfo* MergeFontInfos();
+
+ private:
+  FontIdMap fonts_;
+};
+}
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_MERGER_H_
diff --git a/sfntly/cpp/src/sample/subtly/merger_main.cc b/sfntly/cpp/src/sample/subtly/merger_main.cc
new file mode 100644
index 0000000..a977aa7
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/merger_main.cc
@@ -0,0 +1,69 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <map>
+#include <utility>
+
+#include "sfntly/font.h"
+#include "subtly/merger.h"
+#include "subtly/stats.h"
+#include "subtly/utils.h"
+
+using namespace subtly;
+
+void PrintUsage(const char* program_name) {
+  fprintf(stdout, "Usage: %s <input_font_file1> <input_font_file2> ..."
+          "<input_font_filen> <output_font_file>\n",
+          program_name);
+}
+
+void CheckLoading(const char* font_path, Font* font) {
+  if (!font || font->num_tables() == 0) {
+    fprintf(stderr, "Could not load font %s. Terminating.\n", font_path);
+    exit(1);
+  }
+}
+
+int main(int argc, const char** argv) {
+  if (argc < 3) {
+    PrintUsage(argv[0]);
+    exit(1);
+  }
+
+  FontArray fonts;
+  for (int32_t i = 1; i < argc - 1; ++i) {
+    Ptr<Font> font;
+    font.Attach(LoadFont(argv[i]));
+    CheckLoading(argv[i], font);
+    fonts.push_back(font);
+  }
+
+  Ptr<Merger> merger = new Merger(&fonts);
+  FontPtr new_font;
+  new_font.Attach(merger->Merge());
+
+  fprintf(stderr, "Serializing font to %s\n", argv[argc - 1]);
+  SerializeFont(argv[argc - 1], new_font);
+  if (!new_font) {
+    fprintf(stdout, "Cannot create merged font.\n");
+    return 1;
+  }
+
+  return 0;
+}
diff --git a/sfntly/cpp/src/sample/subtly/stats.cc b/sfntly/cpp/src/sample/subtly/stats.cc
new file mode 100644
index 0000000..769f691
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/stats.cc
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+
+#include "sfntly/font.h"
+#include "sfntly/table/table.h"
+#include "sfntly/tag.h"
+#include "subtly/stats.h"
+
+namespace subtly {
+using namespace sfntly;
+
+int32_t TotalFontSize(Font* font) {
+  int32_t size = 0;
+  const TableMap* table_map = font->GetTableMap();
+  for (TableMap::const_iterator it = table_map->begin(),
+           e = table_map->end(); it != e; ++it) {
+    size += it->second->DataLength();
+  }
+  return size;
+}
+
+double TableSizePercent(Font* font, int32_t tag) {
+  TablePtr table = font->GetTable(tag);
+  return static_cast<double>(table->DataLength()) / TotalFontSize(font) * 100;
+}
+
+void PrintComparison(FILE* out, Font* font, Font* new_font) {
+  fprintf(out, "====== Table Comparison (original v. subset) ======\n");
+  const TableMap* tables = font->GetTableMap();
+  for (TableMap::const_iterator it = tables->begin(),
+           e = tables->end(); it != e; ++it) {
+    char *name = TagToString(it->first);
+    int32_t size = it->second->DataLength();
+    fprintf(out, "-- %s: %d (%lf%%) ", name, size,
+            TableSizePercent(font, it->first));
+    delete[] name;
+
+    Ptr<FontDataTable> new_table = new_font->GetTable(it->first);
+    int32_t new_size = 0;
+    double size_percent = 0;
+    if (new_table) {
+      new_size = new_table->DataLength();
+      size_percent = subtly::TableSizePercent(new_font, it->first);
+    }
+
+    if (new_size == size) {
+      fprintf(out, "| same size\n");
+    } else {
+      fprintf(out, "-> %d (%lf%%) | %lf%% of original\n", new_size,
+              size_percent, static_cast<double>(new_size) / size * 100);
+    }
+  }
+}
+
+void PrintStats(FILE* out, Font* font) {
+  fprintf(out, "====== Table Stats ======\n");
+  const TableMap* tables = font->GetTableMap();
+  for (TableMap::const_iterator it = tables->begin(),
+           e = tables->end(); it != e; ++it) {
+    char *name = TagToString(it->first);
+    int32_t size = it->second->DataLength();
+    fprintf(out, "-- %s: %d (%lf%%)\n", name, size,
+            TableSizePercent(font, it->first));
+    delete[] name;
+  }
+}
+}
diff --git a/sfntly/cpp/src/sample/subtly/stats.h b/sfntly/cpp/src/sample/subtly/stats.h
new file mode 100644
index 0000000..89ef2ae
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/stats.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_STATS_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_STATS_H_
+
+#include <stdio.h>
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+class Font;
+}
+
+namespace subtly {
+using namespace sfntly;
+
+int32_t TotalFontSize(Font* font);
+
+double TableSizePercent(Font* font, int32_t tag);
+
+void PrintComparison(FILE* out, Font* font, Font* new_font);
+
+void PrintStats(FILE* out, Font* font);
+}
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_STATS_H_
diff --git a/sfntly/cpp/src/sample/subtly/subsetter.cc b/sfntly/cpp/src/sample/subtly/subsetter.cc
new file mode 100644
index 0000000..d09627c
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/subsetter.cc
@@ -0,0 +1,67 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "subtly/subsetter.h"
+
+#include <stdio.h>
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/tag.h"
+#include "subtly/character_predicate.h"
+#include "subtly/font_assembler.h"
+#include "subtly/font_info.h"
+#include "subtly/utils.h"
+
+namespace subtly {
+using namespace sfntly;
+
+/******************************************************************************
+ * Subsetter class
+ ******************************************************************************/
+Subsetter::Subsetter(Font* font, CharacterPredicate* predicate)
+    : font_(font),
+      predicate_(predicate) {
+}
+
+Subsetter::Subsetter(const char* font_path, CharacterPredicate* predicate)
+    : predicate_(predicate) {
+  font_.Attach(LoadFont(font_path));
+}
+
+CALLER_ATTACH Font* Subsetter::Subset() {
+  Ptr<FontSourcedInfoBuilder> info_builder =
+      new FontSourcedInfoBuilder(font_, 0, predicate_);
+
+  Ptr<FontInfo> font_info;
+  font_info.Attach(info_builder->GetFontInfo());
+  if (!font_info) {
+#if defined (SUBTLY_DEBUG)
+    fprintf(stderr,
+            "Couldn't create font info. No subset will be generated.\n");
+#endif
+    return NULL;
+  }
+  IntegerSet* table_blacklist = new IntegerSet;
+  table_blacklist->insert(Tag::DSIG);
+  Ptr<FontAssembler> font_assembler = new FontAssembler(font_info,
+                                                        table_blacklist);
+  Ptr<Font> font_subset;
+  font_subset.Attach(font_assembler->Assemble());
+  delete table_blacklist;
+  return font_subset.Detach();
+}
+}
diff --git a/sfntly/cpp/src/sample/subtly/subsetter.h b/sfntly/cpp/src/sample/subtly/subsetter.h
new file mode 100644
index 0000000..a93747f
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/subsetter.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_SUBSETTER_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_SUBSETTER_H_
+
+#include "sfntly/font.h"
+// Cannot remove this header due to Ptr<T> instantiation issue
+#include "subtly/character_predicate.h"
+
+namespace subtly {
+// Subsets a given font using a character predicate.
+class Subsetter : public sfntly::RefCounted<Subsetter> {
+ public:
+  Subsetter(sfntly::Font* font, CharacterPredicate* predicate);
+  Subsetter(const char* font_path, CharacterPredicate* predicate);
+  virtual ~Subsetter() { }
+
+  // Performs subsetting returning the subsetted font.
+  virtual CALLER_ATTACH sfntly::Font* Subset();
+
+ private:
+  sfntly::Ptr<sfntly::Font> font_;
+  sfntly::Ptr<CharacterPredicate> predicate_;
+};
+}
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_SUBSETTER_H_
diff --git a/sfntly/cpp/src/sample/subtly/subsetter_main.cc b/sfntly/cpp/src/sample/subtly/subsetter_main.cc
new file mode 100644
index 0000000..d438148
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/subsetter_main.cc
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <map>
+#include <utility>
+
+#include "sfntly/font.h"
+#include "subtly/character_predicate.h"
+#include "subtly/stats.h"
+#include "subtly/subsetter.h"
+#include "subtly/utils.h"
+
+using namespace subtly;
+
+void PrintUsage(const char* program_name) {
+  fprintf(stdout, "Usage: %s <input_font_file> <output_font_file>"
+          "<start_char> <end_char>\n", program_name);
+}
+
+int main(int argc, const char** argv) {
+  const char* program_name = argv[0];
+  if (argc < 5) {
+    PrintUsage(program_name);
+    exit(1);
+  }
+
+  const char* input_font_path = argv[1];
+  const char* output_font_path = argv[2];
+  FontPtr font;
+  font.Attach(subtly::LoadFont(input_font_path));
+  if (font->num_tables() == 0) {
+    fprintf(stderr, "Could not load font %s.\n", input_font_path);
+    exit(1);
+  }
+
+  const char* start_char = argv[3];
+  const char* end_char = argv[4];
+  if (start_char[1] != 0) {
+    fprintf(stderr, "Start character %c invalid.\n", start_char[0]);
+    exit(1);
+  }
+  if (end_char[1] != 0) {
+    fprintf(stderr, "Start character %c invalid.\n", end_char[0]);
+    exit(1);
+  }
+  int32_t original_size = TotalFontSize(font);
+
+
+  Ptr<CharacterPredicate> range_predicate =
+      new AcceptRange(start_char[0], end_char[0]);
+  Ptr<Subsetter> subsetter = new Subsetter(font, range_predicate);
+  Ptr<Font> new_font;
+  new_font.Attach(subsetter->Subset());
+  if (!new_font) {
+    fprintf(stdout, "Cannot create subset.\n");
+    return 0;
+  }
+
+  subtly::SerializeFont(output_font_path, new_font);
+  subtly::PrintComparison(stdout, font, new_font);
+  int32_t new_size = TotalFontSize(new_font);
+  fprintf(stdout, "Went from %d to %d: %lf%% of original\n",
+          original_size, new_size,
+          static_cast<double>(new_size) / original_size * 100);
+  return 0;
+}
diff --git a/sfntly/cpp/src/sample/subtly/utils.cc b/sfntly/cpp/src/sample/subtly/utils.cc
new file mode 100644
index 0000000..3c204d3
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/utils.cc
@@ -0,0 +1,91 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "subtly/utils.h"
+
+#include "sfntly/data/growable_memory_byte_array.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/port/file_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+
+namespace subtly {
+using namespace sfntly;
+
+CALLER_ATTACH Font* LoadFont(const char* font_path) {
+  Ptr<FontFactory> font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  FontArray fonts;
+  LoadFonts(font_path, font_factory, &fonts);
+  return fonts[0].Detach();
+}
+
+CALLER_ATTACH Font::Builder* LoadFontBuilder(const char* font_path) {
+  FontFactoryPtr font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray builders;
+  LoadFontBuilders(font_path, font_factory, &builders);
+  return builders[0].Detach();
+}
+
+void LoadFonts(const char* font_path, FontFactory* factory, FontArray* fonts) {
+  FileInputStream input_stream;
+  input_stream.Open(font_path);
+  factory->LoadFonts(&input_stream, fonts);
+  input_stream.Close();
+}
+
+void LoadFontBuilders(const char* font_path,
+                      FontFactory* factory,
+                      FontBuilderArray* builders) {
+  FileInputStream input_stream;
+  input_stream.Open(font_path);
+  factory->LoadFontsForBuilding(&input_stream, builders);
+  input_stream.Close();
+}
+
+bool SerializeFont(const char* font_path, Font* font) {
+  if (!font_path)
+    return false;
+  FontFactoryPtr font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  return SerializeFont(font_path, font_factory, font);
+}
+
+bool SerializeFont(const char* font_path, FontFactory* factory, Font* font) {
+  if (!font_path || !factory || !font)
+    return false;
+  // Serializing the font to a stream.
+  MemoryOutputStream output_stream;
+  factory->SerializeFont(font, &output_stream);
+  // Serializing the stream to a file.
+  FILE* output_file = NULL;
+#if defined WIN32
+  fopen_s(&output_file, font_path, "wb");
+#else
+  output_file = fopen(font_path, "wb");
+#endif
+  if (output_file == reinterpret_cast<FILE*>(NULL))
+    return false;
+  for (size_t i = 0; i < output_stream.Size(); ++i) {
+    fwrite(&(output_stream.Get()[i]), 1, 1, output_file);
+  }
+  fflush(output_file);
+  fclose(output_file);
+  return true;
+}
+};
diff --git a/sfntly/cpp/src/sample/subtly/utils.h b/sfntly/cpp/src/sample/subtly/utils.h
new file mode 100644
index 0000000..ba9f0d4
--- /dev/null
+++ b/sfntly/cpp/src/sample/subtly/utils.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_UTILS_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_UTILS_H_
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+
+namespace subtly {
+CALLER_ATTACH sfntly::Font* LoadFont(const char* font_path);
+CALLER_ATTACH sfntly::Font::Builder* LoadFontBuilder(const char* font_path);
+
+void LoadFonts(const char* font_path, sfntly::FontFactory* factory,
+               sfntly::FontArray* fonts);
+void LoadFontBuilders(const char* font_path,
+                      sfntly::FontFactory* factory,
+                      sfntly::FontBuilderArray* builders);
+
+bool SerializeFont(const char* font_path, sfntly::Font* font);
+bool SerializeFont(const char* font_path, sfntly::FontFactory* factory,
+                   sfntly::Font* font);
+}
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SAMPLE_SUBTLY_UTILS_H_
diff --git a/sfntly/cpp/src/sfntly/data/byte_array.cc b/sfntly/cpp/src/sfntly/data/byte_array.cc
new file mode 100644
index 0000000..915a40c
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/byte_array.cc
@@ -0,0 +1,199 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/data/byte_array.h"
+
+#include <algorithm>
+
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+
+const int32_t ByteArray::COPY_BUFFER_SIZE = 8192;
+
+ByteArray::~ByteArray() {}
+
+int32_t ByteArray::Length() { return filled_length_; }
+int32_t ByteArray::Size() { return storage_length_; }
+
+int32_t ByteArray::SetFilledLength(int32_t filled_length) {
+  filled_length_ = std::min<int32_t>(filled_length, storage_length_);
+  return filled_length_;
+}
+
+int32_t ByteArray::Get(int32_t index) {
+  return InternalGet(index) & 0xff;
+}
+
+int32_t ByteArray::Get(int32_t index, ByteVector* b) {
+  assert(b);
+  return Get(index, &((*b)[0]), 0, b->size());
+}
+
+int32_t ByteArray::Get(int32_t index,
+                       byte_t* b,
+                       int32_t offset,
+                       int32_t length) {
+  assert(b);
+  if (index < 0 || index >= filled_length_) {
+    return 0;
+  }
+  int32_t actual_length = std::min<int32_t>(length, filled_length_ - index);
+  return InternalGet(index, b, offset, actual_length);
+}
+
+void ByteArray::Put(int32_t index, byte_t b) {
+  if (index < 0 || index >= Size()) {
+#if defined (SFNTLY_NO_EXCEPTION)
+    return;
+#else
+    throw IndexOutOfBoundException(
+        "Attempt to write outside the bounds of the data");
+#endif
+  }
+  InternalPut(index, b);
+  filled_length_ = std::max<int32_t>(filled_length_, index + 1);
+}
+
+int32_t ByteArray::Put(int index, ByteVector* b) {
+  assert(b);
+  return Put(index, &((*b)[0]), 0, b->size());
+}
+
+int32_t ByteArray::Put(int32_t index,
+                       byte_t* b,
+                       int32_t offset,
+                       int32_t length) {
+  assert(b);
+  if (index < 0 || index >= Size()) {
+#if defined (SFNTLY_NO_EXCEPTION)
+    return 0;
+#else
+    throw IndexOutOfBoundException(
+        "Attempt to write outside the bounds of the data");
+#endif
+  }
+  int32_t actual_length = std::min<int32_t>(length, Size() - index);
+  int32_t bytes_written = InternalPut(index, b, offset, actual_length);
+  filled_length_ = std::max<int32_t>(filled_length_, index + bytes_written);
+  return bytes_written;
+}
+
+int32_t ByteArray::CopyTo(ByteArray* array) {
+  return CopyTo(array, 0, Length());
+}
+
+int32_t ByteArray::CopyTo(ByteArray* array, int32_t offset, int32_t length) {
+  return CopyTo(0, array, offset, length);
+}
+
+int32_t ByteArray::CopyTo(int32_t dst_offset, ByteArray* array,
+                          int32_t src_offset, int32_t length) {
+  assert(array);
+  if (array->Size() < dst_offset + length) {  // insufficient space
+    return -1;
+  }
+
+  ByteVector b(COPY_BUFFER_SIZE);
+  int32_t bytes_read = 0;
+  int32_t index = 0;
+  int32_t remaining_length = length;
+  int32_t buffer_length = std::min<int32_t>(COPY_BUFFER_SIZE, length);
+  while ((bytes_read =
+              Get(index + src_offset, &(b[0]), 0, buffer_length)) > 0) {
+    int bytes_written = array->Put(index + dst_offset, &(b[0]), 0, bytes_read);
+    UNREFERENCED_PARAMETER(bytes_written);
+    index += bytes_read;
+    remaining_length -= bytes_read;
+    buffer_length = std::min<int32_t>(b.size(), remaining_length);
+  }
+  return index;
+}
+
+int32_t ByteArray::CopyTo(OutputStream* os) {
+    return CopyTo(os, 0, Length());
+}
+
+int32_t ByteArray::CopyTo(OutputStream* os, int32_t offset, int32_t length) {
+  ByteVector b(COPY_BUFFER_SIZE);
+  int32_t bytes_read = 0;
+  int32_t index = 0;
+  int32_t buffer_length = std::min<int32_t>(COPY_BUFFER_SIZE, length);
+  while ((bytes_read = Get(index + offset, &(b[0]), 0, buffer_length)) > 0) {
+    os->Write(&b, 0, bytes_read);
+    index += bytes_read;
+    buffer_length = std::min<int32_t>(b.size(), length - index);
+  }
+  return index;
+}
+
+bool ByteArray::CopyFrom(InputStream* is, int32_t length) {
+  ByteVector b(COPY_BUFFER_SIZE);
+  int32_t bytes_read = 0;
+  int32_t index = 0;
+  int32_t buffer_length = std::min<int32_t>(COPY_BUFFER_SIZE, length);
+  while ((bytes_read = is->Read(&b, 0, buffer_length)) > 0) {
+    if (Put(index, &(b[0]), 0, bytes_read) != bytes_read) {
+#if defined (SFNTLY_NO_EXCEPTION)
+      return 0;
+#else
+      throw IOException("Error writing bytes.");
+#endif
+    }
+    index += bytes_read;
+    length -= bytes_read;
+    buffer_length = std::min<int32_t>(b.size(), length);
+  }
+  return true;
+}
+
+bool ByteArray::CopyFrom(InputStream* is) {
+  ByteVector b(COPY_BUFFER_SIZE);
+  int32_t bytes_read = 0;
+  int32_t index = 0;
+  int32_t buffer_length = COPY_BUFFER_SIZE;
+  while ((bytes_read = is->Read(&b, 0, buffer_length)) > 0) {
+    if (Put(index, &b[0], 0, bytes_read) != bytes_read) {
+#if defined (SFNTLY_NO_EXCEPTION)
+      return 0;
+#else
+      throw IOException("Error writing bytes.");
+#endif
+    }
+    index += bytes_read;
+  }
+  return true;
+}
+
+ByteArray::ByteArray(int32_t filled_length,
+                     int32_t storage_length,
+                     bool growable) {
+  Init(filled_length, storage_length, growable);
+}
+
+ByteArray::ByteArray(int32_t filled_length, int32_t storage_length) {
+  Init(filled_length, storage_length, false);
+}
+
+void ByteArray::Init(int32_t filled_length,
+                     int32_t storage_length,
+                     bool growable) {
+  storage_length_ = storage_length;
+  growable_ = growable;
+  SetFilledLength(filled_length);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/byte_array.h b/sfntly/cpp/src/sfntly/data/byte_array.h
new file mode 100644
index 0000000..70dc92f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/byte_array.h
@@ -0,0 +1,201 @@
+/*
+ * Copyright (C) 2011 The sfntly Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_BYTE_ARRAY_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_BYTE_ARRAY_H_
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/port/type.h"
+#include "sfntly/port/input_stream.h"
+#include "sfntly/port/output_stream.h"
+
+namespace sfntly {
+
+// An abstraction to a contiguous array of bytes.
+// C++ port of this class assumes that the data are stored in a linear region
+// like std::vector.
+class ByteArray : virtual public RefCount {
+ public:
+  virtual ~ByteArray();
+
+  // Gets the current filled and readable length of the array.
+  int32_t Length();
+
+  // Gets the maximum size of the array. This is the maximum number of bytes that
+  // the array can hold and all of it may not be filled with data or even fully
+  // allocated yet.
+  int32_t Size();
+
+  // Determines whether or not this array is growable or of fixed size.
+  bool growable() { return growable_; }
+
+  int32_t SetFilledLength(int32_t filled_length);
+
+  // Gets the byte from the given index.
+  // @param index the index into the byte array
+  // @return the byte or -1 if reading beyond the bounds of the data
+  virtual int32_t Get(int32_t index);
+
+  // Gets the bytes from the given index and fill the buffer with them. As many
+  // bytes as will fit into the buffer are read unless that would go past the
+  // end of the array.
+  // @param index the index into the byte array
+  // @param b the buffer to put the bytes read into
+  // @return the number of bytes read from the buffer
+  virtual int32_t Get(int32_t index, ByteVector* b);
+
+  // Gets the bytes from the given index and fill the buffer with them starting
+  // at the offset given. As many bytes as the specified length are read unless
+  // that would go past the end of the array.
+  // @param index the index into the byte array
+  // @param b the buffer to put the bytes read into
+  // @param offset the location in the buffer to start putting the bytes
+  // @param length the number of bytes to put into the buffer
+  // @return the number of bytes read from the buffer
+  virtual int32_t Get(int32_t index,
+                      byte_t* b,
+                      int32_t offset,
+                      int32_t length);
+
+  // Puts the specified byte into the array at the given index unless that would
+  // be beyond the length of the array and it isn't growable.
+  virtual void Put(int32_t index, byte_t b);
+
+  // Puts the specified bytes into the array at the given index. The entire
+  // buffer is put into the array unless that would extend beyond the length and
+  // the array isn't growable.
+  virtual int32_t Put(int32_t index, ByteVector* b);
+
+  // Puts the specified bytes into the array at the given index. All of the bytes
+  // specified are put into the array unless that would extend beyond the length
+  // and the array isn't growable. The bytes to be put into the array are those
+  // in the buffer from the given offset and for the given length.
+  // @param index the index into the ByteArray
+  // @param b the bytes to put into the array
+  // @param offset the offset in the bytes to start copying from
+  // @param length the number of bytes to copy into the array
+  // @return the number of bytes actually written
+  virtual int32_t Put(int32_t index,
+                      byte_t* b,
+                      int32_t offset,
+                      int32_t length);
+
+  // Fully copies this ByteArray to another ByteArray to the extent that the
+  // destination array has storage for the data copied.
+  virtual int32_t CopyTo(ByteArray* array);
+
+  // Copies a segment of this ByteArray to another ByteArray.
+  // @param array the destination
+  // @param offset the offset in this ByteArray to start copying from
+  // @param length the maximum length in bytes to copy
+  // @return the number of bytes copied
+  virtual int32_t CopyTo(ByteArray* array, int32_t offset, int32_t length);
+
+  // Copies this ByteArray to another ByteArray.
+  // @param dstOffset the offset in the destination array to start copying to
+  // @param array the destination
+  // @param srcOffset the offset in this ByteArray to start copying from
+  // @param length the maximum length in bytes to copy
+  // @return the number of bytes copied
+  virtual int32_t CopyTo(int32_t dst_offset,
+                         ByteArray* array,
+                         int32_t src_offset,
+                         int32_t length);
+
+  // Copies this ByteArray to an OutputStream.
+  // @param os the destination
+  // @return the number of bytes copied
+  virtual int32_t CopyTo(OutputStream* os);
+
+  // Copies this ByteArray to an OutputStream.
+  // @param os the destination
+  // @param offset
+  // @param length
+  // @return the number of bytes copied
+  virtual int32_t CopyTo(OutputStream* os, int32_t offset, int32_t length);
+
+  // Copies from the InputStream into this ByteArray.
+  // @param is the source
+  // @param length the number of bytes to copy
+  virtual bool CopyFrom(InputStream* is, int32_t length);
+
+  // Copies everything from the InputStream into this ByteArray.
+  // @param is the source
+  virtual bool CopyFrom(InputStream* is);
+
+ protected:
+  // filledLength the length that is "filled" and readable counting from offset.
+  // storageLength the maximum storage size of the underlying data.
+  // growable is the storage growable - storageLength is the max growable size.
+  ByteArray(int32_t filled_length, int32_t storage_length, bool growable);
+  ByteArray(int32_t filled_length, int32_t storage_length);
+  void Init(int32_t filled_length, int32_t storage_length, bool growable);
+
+  // Internal subclass API
+
+  // Stores the byte at the index given.
+  // @param index the location to store at
+  // @param b the byte to store
+  virtual void InternalPut(int32_t index, byte_t b) = 0;
+
+  // Stores the array of bytes at the given index.
+  // @param index the location to store at
+  // @param b the bytes to store
+  // @param offset the offset to start from in the byte array
+  // @param length the length of the byte array to store from the offset
+  // @return the number of bytes actually stored
+  virtual int32_t InternalPut(int32_t index,
+                              byte_t* b,
+                              int32_t offset,
+                              int32_t length) = 0;
+
+  // Gets the byte at the index given.
+  // @param index the location to get from
+  // @return the byte stored at the index
+  virtual byte_t InternalGet(int32_t index) = 0;
+
+  // Gets the bytes at the index given of the given length.
+  // @param index the location to start getting from
+  // @param b the array to put the bytes into
+  // @param offset the offset in the array to put the bytes into
+  // @param length the length of bytes to read
+  // @return the number of bytes actually ready
+  virtual int32_t InternalGet(int32_t index,
+                              byte_t* b,
+                              int32_t offset,
+                              int32_t length) = 0;
+
+  // Close this instance of the ByteArray.
+  virtual void Close() = 0;
+
+  // C++ port only, raw pointer to the first element of storage.
+  virtual byte_t* Begin() = 0;
+
+  // Java toString() not ported.
+
+  static const int32_t COPY_BUFFER_SIZE;
+
+ private:
+  //bool bound_;  // unused, comment out
+  int32_t filled_length_;
+  int32_t storage_length_;
+  bool growable_;
+};
+typedef Ptr<ByteArray> ByteArrayPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_BYTE_ARRAY_H_
diff --git a/sfntly/cpp/src/sfntly/data/font_data.cc b/sfntly/cpp/src/sfntly/data/font_data.cc
new file mode 100644
index 0000000..d2b95ea
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/font_data.cc
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <limits.h>
+#include <algorithm>
+#include <functional>
+
+#include "sfntly/data/font_data.h"
+
+namespace sfntly {
+
+int32_t FontData::Size() const {
+  return std::min<int32_t>(array_->Size() - bound_offset_, bound_length_);
+}
+
+bool FontData::Bound(int32_t offset, int32_t length) {
+  if (offset + length > Size() || offset < 0 || length < 0)
+    return false;
+
+  bound_offset_ += offset;
+  bound_length_ = length;
+  return true;
+}
+
+bool FontData::Bound(int32_t offset) {
+if (offset > Size() || offset < 0)
+    return false;
+
+  bound_offset_ += offset;
+  return true;
+}
+
+int32_t FontData::Length() const {
+  return std::min<int32_t>(array_->Length() - bound_offset_, bound_length_);
+}
+
+FontData::FontData(ByteArray* ba) {
+  Init(ba);
+}
+
+FontData::FontData(FontData* data, int32_t offset, int32_t length) {
+  Init(data->array_);
+  Bound(data->bound_offset_ + offset, length);
+}
+
+FontData::FontData(FontData* data, int32_t offset) {
+  Init(data->array_);
+  Bound(data->bound_offset_ + offset,
+        (data->bound_length_ == GROWABLE_SIZE)
+            ? GROWABLE_SIZE : data->bound_length_ - offset);
+}
+
+FontData::~FontData() {}
+
+void FontData::Init(ByteArray* ba) {
+  array_ = ba;
+  bound_offset_ = 0;
+  bound_length_ = GROWABLE_SIZE;
+}
+
+int32_t FontData::BoundOffset(int32_t offset) {
+  return offset + bound_offset_;
+}
+
+int32_t FontData::BoundLength(int32_t offset, int32_t length) {
+  return std::min<int32_t>(length, bound_length_ - offset);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/font_data.h b/sfntly/cpp/src/sfntly/data/font_data.h
new file mode 100644
index 0000000..d02e8b7
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/font_data.h
@@ -0,0 +1,135 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_DATA_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_DATA_H_
+
+#include <limits.h>
+
+#include <vector>
+
+#include "sfntly/port/type.h"
+#include "sfntly/data/byte_array.h"
+#include "sfntly/port/refcount.h"
+
+namespace sfntly {
+
+struct DataSize {
+  enum {
+    kBYTE = 1,
+    kCHAR = 1,
+    kUSHORT = 2,
+    kSHORT = 2,
+    kUINT24 = 3,
+    kULONG = 4,
+    kLONG = 4,
+    kFixed = 4,
+    kFUNIT = 4,
+    kFWORD = 2,
+    kUFWORD = 2,
+    kF2DOT14 = 2,
+    kLONGDATETIME = 8,
+    kTag = 4,
+    kGlyphID = 2,
+    kOffset = 2
+  };
+};
+
+class FontData : virtual public RefCount {
+ public:
+  // Gets the maximum size of the FontData. This is the maximum number of bytes
+  // that the font data can hold and all of it may not be filled with data or
+  // even fully allocated yet.
+  // @return the maximum size of this font data
+  virtual int32_t Size() const;
+
+  // Sets limits on the size of the FontData. The FontData is then only
+  // visible within the bounds set.
+  // @param offset the start of the new bounds
+  // @param length the number of bytes in the bounded array
+  // @return true if the bounding range was successful; false otherwise
+  virtual bool Bound(int32_t offset, int32_t length);
+
+  // Sets limits on the size of the FontData. This is a offset bound only so if
+  // the FontData is writable and growable then there is no limit to that growth
+  // from the bounding operation.
+  // @param offset the start of the new bounds which must be within the current
+  //        size of the FontData
+  // @return true if the bounding range was successful; false otherwise
+  virtual bool Bound(int32_t offset);
+
+  // Makes a slice of this FontData. The returned slice will share the data with
+  // the original <code>FontData</code>.
+  // @param offset the start of the slice
+  // @param length the number of bytes in the slice
+  // @return a slice of the original FontData
+  virtual CALLER_ATTACH FontData* Slice(int32_t offset, int32_t length) = 0;
+
+  // Makes a bottom bound only slice of this array. The returned slice will
+  // share the data with the original <code>FontData</code>.
+  // @param offset the start of the slice
+  // @return a slice of the original FontData
+  virtual CALLER_ATTACH FontData* Slice(int32_t offset) = 0;
+
+  // Gets the length of the data.
+  virtual int32_t Length() const;
+
+ protected:
+  // Constructor.
+  // @param ba the byte array to use for the backing data
+  explicit FontData(ByteArray* ba);
+
+  // Constructor.
+  // @param data the data to wrap
+  // @param offset the offset to start the wrap from
+  // @param length the length of the data wrapped
+  FontData(FontData* data, int32_t offset, int32_t length);
+
+  // Constructor.
+  // @param data the data to wrap
+  // @param offset the offset to start the wrap from
+  FontData(FontData* data, int32_t offset);
+  virtual ~FontData();
+
+  void Init(ByteArray* ba);
+
+  // Gets the offset in the underlying data taking into account any bounds on
+  // the data.
+  // @param offset the offset to get the bound compensated offset for
+  // @return the bound compensated offset
+  int32_t BoundOffset(int32_t offset);
+
+  // Gets the length in the underlying data taking into account any bounds on
+  // the data.
+  // @param offset the offset that the length is being used at
+  // @param length the length to get the bound compensated length for
+  // @return the bound compensated length
+  int32_t BoundLength(int32_t offset, int32_t length);
+
+  static const int32_t GROWABLE_SIZE = INT_MAX;
+
+  // TODO(arthurhsu): style guide violation: refactor this protected member
+  ByteArrayPtr array_;
+
+ private:
+  int32_t bound_offset_;
+  int32_t bound_length_;
+};
+typedef Ptr<FontData> FontDataPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_DATA_H_
diff --git a/sfntly/cpp/src/sfntly/data/font_input_stream.cc b/sfntly/cpp/src/sfntly/data/font_input_stream.cc
new file mode 100644
index 0000000..dcf8be3
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/font_input_stream.cc
@@ -0,0 +1,141 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/data/font_input_stream.h"
+
+#include <algorithm>
+
+namespace sfntly {
+
+FontInputStream::FontInputStream(InputStream* is)
+    : stream_(is), position_(0), length_(0), bounded_(false) {
+}
+
+FontInputStream::FontInputStream(InputStream* is, size_t length)
+    : stream_(is), position_(0), length_(length), bounded_(true) {
+}
+
+FontInputStream::~FontInputStream() {
+  // Do not close here, underlying InputStream will close themselves.
+}
+
+int32_t FontInputStream::Available() {
+  if (stream_) {
+    return stream_->Available();
+  }
+  return 0;
+}
+
+void FontInputStream::Close() {
+  if (stream_) {
+    stream_->Close();
+  }
+}
+
+void FontInputStream::Mark(int32_t readlimit) {
+  if (stream_) {
+    stream_->Mark(readlimit);
+  }
+}
+
+bool FontInputStream::MarkSupported() {
+  if (stream_) {
+    return stream_->MarkSupported();
+  }
+  return false;
+}
+
+void FontInputStream::Reset() {
+  if (stream_) {
+    stream_->Reset();
+  }
+}
+
+int32_t FontInputStream::Read() {
+  if (!stream_ || (bounded_ && position_ >= length_)) {
+    return -1;
+  }
+  int32_t b = stream_->Read();
+  if (b >= 0) {
+    position_++;
+  }
+  return b;
+}
+
+int32_t FontInputStream::Read(ByteVector* b, int32_t offset, int32_t length) {
+  if (!stream_ || offset < 0 || length < 0 ||
+      (bounded_ && position_ >= length_)) {
+    return -1;
+  }
+  int32_t bytes_to_read =
+      bounded_ ? std::min<int32_t>(length, (int32_t)(length_ - position_)) :
+                 length;
+  int32_t bytes_read = stream_->Read(b, offset, bytes_to_read);
+  position_ += bytes_read;
+  return bytes_read;
+}
+
+int32_t FontInputStream::Read(ByteVector* b) {
+  return Read(b, 0, b->size());
+}
+
+int32_t FontInputStream::ReadChar() {
+  return Read();
+}
+
+int32_t FontInputStream::ReadUShort() {
+  return 0xffff & (Read() << 8 | Read());
+}
+
+int32_t FontInputStream::ReadShort() {
+  return ((Read() << 8 | Read()) << 16) >> 16;
+}
+
+int32_t FontInputStream::ReadUInt24() {
+  return 0xffffff & (Read() << 16 | Read() << 8 | Read());
+}
+
+int64_t FontInputStream::ReadULong() {
+  return 0xffffffffL & ReadLong();
+}
+
+int32_t FontInputStream::ReadULongAsInt() {
+  int64_t ulong = ReadULong();
+  return ((int32_t)ulong) & ~0x80000000;
+}
+
+int32_t FontInputStream::ReadLong() {
+  return Read() << 24 | Read() << 16 | Read() << 8 | Read();
+}
+
+int32_t FontInputStream::ReadFixed() {
+  return ReadLong();
+}
+
+int64_t FontInputStream::ReadDateTimeAsLong() {
+  return (int64_t)ReadULong() << 32 | ReadULong();
+}
+
+int64_t FontInputStream::Skip(int64_t n) {
+  if (stream_) {
+    int64_t skipped = stream_->Skip(n);
+    position_ += skipped;
+    return skipped;
+  }
+  return 0;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/font_input_stream.h b/sfntly/cpp/src/sfntly/data/font_input_stream.h
new file mode 100644
index 0000000..9992b07
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/font_input_stream.h
@@ -0,0 +1,97 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_INPUT_STREAM_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_INPUT_STREAM_H_
+
+#include "sfntly/port/type.h"
+#include "sfntly/port/input_stream.h"
+
+namespace sfntly {
+
+// An input stream for reading font data.
+// The data types used are as listed:
+// BYTE       8-bit unsigned integer.
+// CHAR       8-bit signed integer.
+// USHORT     16-bit unsigned integer.
+// SHORT      16-bit signed integer.
+// UINT24     24-bit unsigned integer.
+// ULONG      32-bit unsigned integer.
+// LONG       32-bit signed integer.
+// Fixed      32-bit signed fixed-point number (16.16)
+// FUNIT      Smallest measurable distance in the em space.
+// FWORD      16-bit signed integer (SHORT) that describes a quantity in FUnits.
+// UFWORD     16-bit unsigned integer (USHORT) that describes a quantity in
+//            FUnits.
+// F2DOT14    16-bit signed fixed number with the low 14 bits of fraction (2.14)
+// LONGDATETIME  Date represented in number of seconds since 12:00 midnight,
+//               January 1, 1904. The value is represented as a signed 64-bit
+//               integer.
+
+// Note: Original class inherits from Java's FilterOutputStream, which wraps
+//       an InputStream within.  In C++, we directly do the wrapping without
+//       defining another layer of abstraction.  The wrapped output stream is
+//       *NOT* reference counted (because it's meaningless to ref-count an I/O
+//       stream).
+class FontInputStream : public InputStream {
+ public:
+  // Constructor.
+  // @param is input stream to wrap
+  explicit FontInputStream(InputStream* is);
+
+  // Constructor for a bounded font input stream.
+  // @param is input stream to wrap
+  // @param length the maximum length of bytes to read
+  FontInputStream(InputStream* is, size_t length);
+
+  virtual ~FontInputStream();
+
+
+  virtual int32_t Available();
+  virtual void Close();
+  virtual void Mark(int32_t readlimit);
+  virtual bool MarkSupported();
+  virtual void Reset();
+
+  virtual int32_t Read();
+  virtual int32_t Read(ByteVector* buffer);
+  virtual int32_t Read(ByteVector* buffer, int32_t offset, int32_t length);
+
+  // Get the current position in the stream in bytes.
+  // @return the current position in bytes
+  virtual int64_t position() { return position_; }
+
+  virtual int32_t ReadChar();
+  virtual int32_t ReadUShort();
+  virtual int32_t ReadShort();
+  virtual int32_t ReadUInt24();
+  virtual int64_t ReadULong();
+  virtual int32_t ReadULongAsInt();
+  virtual int32_t ReadLong();
+  virtual int32_t ReadFixed();
+  virtual int64_t ReadDateTimeAsLong();
+  virtual int64_t Skip(int64_t n);  // n can be negative.
+
+ private:
+  InputStream* stream_;
+  int64_t position_;
+  int64_t length_;  // Bound on length of data to read.
+  bool bounded_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_INPUT_STREAM_H_
diff --git a/sfntly/cpp/src/sfntly/data/font_output_stream.cc b/sfntly/cpp/src/sfntly/data/font_output_stream.cc
new file mode 100644
index 0000000..3422a22
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/font_output_stream.cc
@@ -0,0 +1,130 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/data/font_output_stream.h"
+
+#include <algorithm>
+
+namespace sfntly {
+
+FontOutputStream::FontOutputStream(OutputStream* os)
+    : stream_(os),
+      position_(0) {
+}
+
+FontOutputStream::~FontOutputStream() {
+  // Do not close, underlying stream shall clean up themselves.
+}
+
+void FontOutputStream::Write(byte_t b) {
+  if (stream_) {
+    stream_->Write(b);
+    position_++;
+  }
+}
+
+void FontOutputStream::Write(ByteVector* b) {
+  if (b) {
+    Write(b, 0, b->size());
+    position_ += b->size();
+  }
+}
+
+void FontOutputStream::Write(ByteVector* b, int32_t off, int32_t len) {
+  assert(b);
+  assert(stream_);
+  if (off < 0 || len < 0 || off + len < 0 ||
+      static_cast<size_t>(off + len) > b->size()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#else
+    return;
+#endif
+  }
+
+  stream_->Write(b, off, len);
+  position_ += len;
+}
+
+void FontOutputStream::Write(byte_t* b, int32_t off, int32_t len) {
+  assert(b);
+  assert(stream_);
+  if (off < 0 || len < 0 || off + len < 0) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#else
+    return;
+#endif
+  }
+
+  stream_->Write(b, off, len);
+  position_ += len;
+}
+
+void FontOutputStream::WriteChar(byte_t c) {
+  Write(c);
+}
+
+void FontOutputStream::WriteUShort(int32_t us) {
+  Write((byte_t)((us >> 8) & 0xff));
+  Write((byte_t)(us & 0xff));
+}
+
+void FontOutputStream::WriteShort(int32_t s) {
+  WriteUShort(s);
+}
+
+void FontOutputStream::WriteUInt24(int32_t ui) {
+  Write((byte_t)(ui >> 16) & 0xff);
+  Write((byte_t)(ui >> 8) & 0xff);
+  Write((byte_t)ui & 0xff);
+}
+
+void FontOutputStream::WriteULong(int64_t ul) {
+  Write((byte_t)((ul >> 24) & 0xff));
+  Write((byte_t)((ul >> 16) & 0xff));
+  Write((byte_t)((ul >> 8) & 0xff));
+  Write((byte_t)(ul & 0xff));
+}
+
+void FontOutputStream::WriteLong(int64_t l) {
+  WriteULong(l);
+}
+
+void FontOutputStream::WriteFixed(int32_t f) {
+  WriteULong(f);
+}
+
+void FontOutputStream::WriteDateTime(int64_t date) {
+  WriteULong((date >> 32) & 0xffffffff);
+  WriteULong(date & 0xffffffff);
+}
+
+void FontOutputStream::Flush() {
+  if (stream_) {
+    stream_->Flush();
+  }
+}
+
+void FontOutputStream::Close() {
+  if (stream_) {
+    stream_->Flush();
+    stream_->Close();
+    position_ = 0;
+  }
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/font_output_stream.h b/sfntly/cpp/src/sfntly/data/font_output_stream.h
new file mode 100644
index 0000000..fcd48e8
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/font_output_stream.h
@@ -0,0 +1,79 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_OUTPUT_STREAM_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_OUTPUT_STREAM_H_
+
+#include "sfntly/port/type.h"
+#include "sfntly/port/output_stream.h"
+
+namespace sfntly {
+
+// An output stream for writing font data.
+// The data types used are as listed:
+// BYTE       8-bit unsigned integer.
+// CHAR       8-bit signed integer.
+// USHORT     16-bit unsigned integer.
+// SHORT      16-bit signed integer.
+// UINT24     24-bit unsigned integer.
+// ULONG      32-bit unsigned integer.
+// LONG       32-bit signed integer.
+// Fixed      32-bit signed fixed-point number (16.16)
+// FUNIT      Smallest measurable distance in the em space.
+// FWORD      16-bit signed integer (SHORT) that describes a quantity in FUnits.
+// UFWORD     16-bit unsigned integer (USHORT) that describes a quantity in
+//            FUnits.
+// F2DOT14    16-bit signed fixed number with the low 14 bits of fraction (2.14)
+// LONGDATETIME  Date represented in number of seconds since 12:00 midnight,
+//               January 1, 1904. The value is represented as a signed 64-bit
+//               integer.
+
+// Note: The wrapped output stream is *NOT* reference counted (because it's
+//       meaningless to ref-count an I/O stream).
+class FontOutputStream : public OutputStream {
+ public:
+  explicit FontOutputStream(OutputStream* os);
+  virtual ~FontOutputStream();
+
+  virtual size_t position() { return position_; }
+
+  virtual void Write(byte_t b);
+  virtual void Write(ByteVector* b);
+  virtual void Write(ByteVector* b, int32_t off, int32_t len);
+  virtual void Write(byte_t* b, int32_t off, int32_t len);
+  virtual void WriteChar(byte_t c);
+  virtual void WriteUShort(int32_t us);
+  virtual void WriteShort(int32_t s);
+  virtual void WriteUInt24(int32_t ui);
+  virtual void WriteULong(int64_t ul);
+  virtual void WriteLong(int64_t l);
+  virtual void WriteFixed(int32_t l);
+  virtual void WriteDateTime(int64_t date);
+
+  // Note: C++ port only.
+  virtual void Flush();
+  virtual void Close();
+
+ private:
+  // Note: we do not use the variable name out as in Java because it has
+  //       special meaning in VC++ and will be very confusing.
+  OutputStream* stream_;
+  size_t position_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_FONT_OUTPUT_STREAM_H_
diff --git a/sfntly/cpp/src/sfntly/data/growable_memory_byte_array.cc b/sfntly/cpp/src/sfntly/data/growable_memory_byte_array.cc
new file mode 100644
index 0000000..c335614
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/growable_memory_byte_array.cc
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/data/growable_memory_byte_array.h"
+
+#include <limits.h>
+#include <string.h>
+
+#include <algorithm>
+
+namespace sfntly {
+
+GrowableMemoryByteArray::GrowableMemoryByteArray()
+    : ByteArray(0, INT_MAX, true) {
+  // Note: We did not set an initial size of array like Java because STL
+  //       implementation will determine the best strategy.
+}
+
+GrowableMemoryByteArray::~GrowableMemoryByteArray() {}
+
+int32_t GrowableMemoryByteArray::CopyTo(OutputStream* os,
+                                        int32_t offset,
+                                        int32_t length) {
+  assert(os);
+  os->Write(&b_, offset, length);
+  return length;
+}
+
+void GrowableMemoryByteArray::InternalPut(int32_t index, byte_t b) {
+  if ((size_t)index >= b_.size()) {
+    b_.resize((size_t)(index + 1));
+  }
+  b_[index] = b;
+}
+
+int32_t GrowableMemoryByteArray::InternalPut(int32_t index,
+                                             byte_t* b,
+                                             int32_t offset,
+                                             int32_t length) {
+  if ((size_t)index + length >= b_.size()) {
+    // Note: We grow one byte more than Java version. VC debuggers shows
+    //       data better this way.
+    b_.resize((size_t)(index + length + 1));
+  }
+  std::copy(b + offset, b + offset + length, b_.begin() + index);
+  return length;
+}
+
+byte_t GrowableMemoryByteArray::InternalGet(int32_t index) {
+  return b_[index];
+}
+
+int32_t GrowableMemoryByteArray::InternalGet(int32_t index,
+                                             byte_t* b,
+                                             int32_t offset,
+                                             int32_t length) {
+  memcpy(b + offset, &(b_[0]) + index, length);
+  return length;
+}
+
+void GrowableMemoryByteArray::Close() {
+  b_.clear();
+}
+
+byte_t* GrowableMemoryByteArray::Begin() {
+  return &(b_[0]);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/growable_memory_byte_array.h b/sfntly/cpp/src/sfntly/data/growable_memory_byte_array.h
new file mode 100644
index 0000000..8583a0d
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/growable_memory_byte_array.h
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_GROWABLE_MEMORY_BYTE_ARRAY_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_GROWABLE_MEMORY_BYTE_ARRAY_H_
+
+#include "sfntly/data/byte_array.h"
+
+namespace sfntly {
+
+// Note: This is not really a port of Java version. Instead, this wraps a
+//       std::vector inside and let it grow by calling resize().
+class GrowableMemoryByteArray : public ByteArray,
+                                public RefCounted<GrowableMemoryByteArray> {
+ public:
+  GrowableMemoryByteArray();
+  virtual ~GrowableMemoryByteArray();
+  virtual int32_t CopyTo(OutputStream* os, int32_t offset, int32_t length);
+
+  // Make gcc -Woverloaded-virtual happy.
+  virtual int32_t CopyTo(ByteArray* array) { return ByteArray::CopyTo(array); }
+  virtual int32_t CopyTo(ByteArray* array, int32_t offset, int32_t length) {
+    return ByteArray::CopyTo(array, offset, length);
+  }
+  virtual int32_t CopyTo(int32_t dst_offset,
+                         ByteArray* array,
+                         int32_t src_offset,
+                         int32_t length) {
+    return ByteArray::CopyTo(dst_offset, array, src_offset, length);
+  }
+  virtual int32_t CopyTo(OutputStream* os) { return ByteArray::CopyTo(os); }
+
+ protected:
+  virtual void InternalPut(int32_t index, byte_t b);
+  virtual int32_t InternalPut(int32_t index,
+                              byte_t* b,
+                              int32_t offset,
+                              int32_t length);
+  virtual byte_t InternalGet(int32_t index);
+  virtual int32_t InternalGet(int32_t index,
+                              byte_t* b,
+                              int32_t offset,
+                              int32_t length);
+  virtual void Close();
+  virtual byte_t* Begin();
+
+ private:
+  ByteVector b_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_GROWABLE_MEMORY_BYTE_ARRAY_H_
diff --git a/sfntly/cpp/src/sfntly/data/memory_byte_array.cc b/sfntly/cpp/src/sfntly/data/memory_byte_array.cc
new file mode 100644
index 0000000..d6c9c48
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/memory_byte_array.cc
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/data/memory_byte_array.h"
+
+#include <string.h>
+
+namespace sfntly {
+
+MemoryByteArray::MemoryByteArray(int32_t length)
+    : ByteArray(0, length), b_(NULL), allocated_(true) {
+}
+
+MemoryByteArray::MemoryByteArray(byte_t* b, int32_t filled_length)
+    : ByteArray(filled_length, filled_length), b_(b), allocated_(false) {
+  assert(b);
+}
+
+MemoryByteArray::~MemoryByteArray() {
+  Close();
+}
+
+int32_t MemoryByteArray::CopyTo(OutputStream* os,
+                                int32_t offset,
+                                int32_t length) {
+  assert(os);
+  os->Write(b_, offset, length);
+  return length;
+}
+
+void MemoryByteArray::Init() {
+  if (allocated_ && b_ == NULL) {
+    b_ = new byte_t[Size()];
+    memset(b_, 0, Size());
+  }
+}
+
+void MemoryByteArray::InternalPut(int32_t index, byte_t b) {
+  Init();
+  b_[index] = b;
+}
+
+int32_t MemoryByteArray::InternalPut(int32_t index,
+                                     byte_t* b,
+                                     int32_t offset,
+                                     int32_t length) {
+  assert(b);
+  Init();
+  memcpy(b_ + index, b + offset, length);
+  return length;
+}
+
+byte_t MemoryByteArray::InternalGet(int32_t index) {
+  Init();
+  return b_[index];
+}
+
+int32_t MemoryByteArray::InternalGet(int32_t index,
+                                     byte_t* b,
+                                     int32_t offset,
+                                     int32_t length) {
+  assert(b);
+  Init();
+  memcpy(b + offset, b_ + index, length);
+  return length;
+}
+
+void MemoryByteArray::Close() {
+  if (allocated_ && b_) {
+    delete[] b_;
+  }
+  b_ = NULL;
+}
+
+byte_t* MemoryByteArray::Begin() {
+  Init();
+  return b_;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/memory_byte_array.h b/sfntly/cpp/src/sfntly/data/memory_byte_array.h
new file mode 100644
index 0000000..838fd1a
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/memory_byte_array.h
@@ -0,0 +1,81 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_MEMORY_BYTE_ARRAY_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_MEMORY_BYTE_ARRAY_H_
+
+#include "sfntly/data/byte_array.h"
+
+namespace sfntly {
+
+class MemoryByteArray : public ByteArray, public RefCounted<MemoryByteArray> {
+ public:
+  // Construct a new MemoryByteArray with a new array of the size given. It is
+  // assumed that none of the array is filled and readable.
+  explicit MemoryByteArray(int32_t length);
+
+  // Note: not implemented due to dangerous operations in constructor.
+  //explicit MemoryByteArray(ByteVector* b);
+
+  // Construct a new MemoryByteArray using byte array.
+  // @param b the byte array that provides the actual storage
+  // @param filled_length the index of the last byte in the array has data
+  // Note: This is different from Java version, it does not take over the
+  //       ownership of b.  Caller is responsible for handling the lifetime
+  //       of b.  C++ port also assumes filled_length is buffer_length since
+  //       there is not a reliable way to identify the actual size of buffer.
+  MemoryByteArray(byte_t* b, int32_t filled_length);
+
+  virtual ~MemoryByteArray();
+  virtual int32_t CopyTo(OutputStream* os, int32_t offset, int32_t length);
+
+  // Make gcc -Woverloaded-virtual happy.
+  virtual int32_t CopyTo(ByteArray* array) { return ByteArray::CopyTo(array); }
+  virtual int32_t CopyTo(ByteArray* array, int32_t offset, int32_t length) {
+    return ByteArray::CopyTo(array, offset, length);
+  }
+  virtual int32_t CopyTo(int32_t dst_offset,
+                         ByteArray* array,
+                         int32_t src_offset,
+                         int32_t length) {
+    return ByteArray::CopyTo(dst_offset, array, src_offset, length);
+  }
+  virtual int32_t CopyTo(OutputStream* os) { return ByteArray::CopyTo(os); }
+
+ protected:
+  virtual void InternalPut(int32_t index, byte_t b);
+  virtual int32_t InternalPut(int32_t index,
+                              byte_t* b,
+                              int32_t offset,
+                              int32_t length);
+  virtual byte_t InternalGet(int32_t index);
+  virtual int32_t InternalGet(int32_t index,
+                              byte_t* b,
+                              int32_t offset,
+                              int32_t length);
+  virtual void Close();
+  virtual byte_t* Begin();
+
+ private:
+  void Init();  // C++ port only, used to allocate memory outside constructor.
+
+  byte_t* b_;
+  bool allocated_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_MEMORY_BYTE_ARRAY_H_
diff --git a/sfntly/cpp/src/sfntly/data/readable_font_data.cc b/sfntly/cpp/src/sfntly/data/readable_font_data.cc
new file mode 100644
index 0000000..06d783f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/readable_font_data.cc
@@ -0,0 +1,336 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/data/readable_font_data.h"
+
+#include <stdio.h>
+
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/data/writable_font_data.h"
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+
+ReadableFontData::ReadableFontData(ByteArray* array)
+    : FontData(array),
+      checksum_set_(false),
+      checksum_(0) {
+}
+
+ReadableFontData::~ReadableFontData() {}
+
+// TODO(arthurhsu): re-investigate the memory model of this function.  It's
+//                  not too useful without copying, but it's not performance
+//                  savvy to do copying.
+CALLER_ATTACH
+ReadableFontData* ReadableFontData::CreateReadableFontData(ByteVector* b) {
+  assert(b);
+  ByteArrayPtr ba = new MemoryByteArray(b->size());
+  ba->Put(0, b);
+  ReadableFontDataPtr wfd = new ReadableFontData(ba);
+  return wfd.Detach();
+}
+
+int64_t ReadableFontData::Checksum() {
+  AutoLock lock(checksum_lock_);
+  if (!checksum_set_) {
+    ComputeChecksum();
+  }
+  return checksum_;
+}
+
+void ReadableFontData::SetCheckSumRanges(const IntegerList& ranges) {
+  checksum_range_ = ranges;
+  checksum_set_ = false;  // UNIMPLEMENTED: atomicity
+}
+
+int32_t ReadableFontData::ReadUByte(int32_t index) {
+  int32_t b = array_->Get(BoundOffset(index));
+#if !defined (SFNTLY_NO_EXCEPTION)
+  if (b < 0) {
+    throw IndexOutOfBoundException(
+        "Index attempted to be read from is out of bounds", index);
+  }
+#endif
+  return b;
+}
+
+int32_t ReadableFontData::ReadByte(int32_t index) {
+  int32_t b = array_->Get(BoundOffset(index));
+#if !defined (SFNTLY_NO_EXCEPTION)
+  if (b < 0) {
+    throw IndexOutOfBoundException(
+        "Index attempted to be read from is out of bounds", index);
+  }
+#endif
+  return (b << 24) >> 24;
+}
+
+int32_t ReadableFontData::ReadBytes(int32_t index,
+                                    byte_t* b,
+                                    int32_t offset,
+                                    int32_t length) {
+  return array_->Get(BoundOffset(index), b, offset, BoundLength(index, length));
+}
+
+int32_t ReadableFontData::ReadChar(int32_t index) {
+  return ReadUByte(index);
+}
+
+int32_t ReadableFontData::ReadUShort(int32_t index) {
+  return 0xffff & (ReadUByte(index) << 8 | ReadUByte(index + 1));
+}
+
+int32_t ReadableFontData::ReadShort(int32_t index) {
+  return ((ReadByte(index) << 8 | ReadUByte(index + 1)) << 16) >> 16;
+}
+
+int32_t ReadableFontData::ReadUInt24(int32_t index) {
+  return 0xffffff & (ReadUByte(index) << 16 |
+                     ReadUByte(index + 1) << 8 |
+                     ReadUByte(index + 2));
+}
+
+int64_t ReadableFontData::ReadULong(int32_t index) {
+  return 0xffffffffL & (ReadUByte(index) << 24 |
+                        ReadUByte(index + 1) << 16 |
+                        ReadUByte(index + 2) << 8 |
+                        ReadUByte(index + 3));
+}
+
+int32_t ReadableFontData::ReadULongAsInt(int32_t index) {
+  int64_t ulong = ReadULong(index);
+#if !defined (SFNTLY_NO_EXCEPTION)
+  if ((ulong & 0x80000000) == 0x80000000) {
+    throw ArithmeticException("Long value too large to fit into an integer.");
+  }
+#endif
+  return static_cast<int32_t>(ulong);
+}
+
+int64_t ReadableFontData::ReadULongLE(int32_t index) {
+  return 0xffffffffL & (ReadUByte(index) |
+                        ReadUByte(index + 1) << 8 |
+                        ReadUByte(index + 2) << 16 |
+                        ReadUByte(index + 3) << 24);
+}
+
+int32_t ReadableFontData::ReadLong(int32_t index) {
+  return ReadByte(index) << 24 |
+         ReadUByte(index + 1) << 16 |
+         ReadUByte(index + 2) << 8 |
+         ReadUByte(index + 3);
+}
+
+int32_t ReadableFontData::ReadFixed(int32_t index) {
+  return ReadLong(index);
+}
+
+int64_t ReadableFontData::ReadDateTimeAsLong(int32_t index) {
+  return (int64_t)ReadULong(index) << 32 | ReadULong(index + 4);
+}
+
+int32_t ReadableFontData::ReadFWord(int32_t index) {
+  return ReadShort(index);
+}
+
+int32_t ReadableFontData::ReadFUFWord(int32_t index) {
+  return ReadUShort(index);
+}
+
+int32_t ReadableFontData::CopyTo(OutputStream* os) {
+  return array_->CopyTo(os, BoundOffset(0), Length());
+}
+
+int32_t ReadableFontData::CopyTo(WritableFontData* wfd) {
+  return array_->CopyTo(wfd->BoundOffset(0),
+                        wfd->array_,
+                        BoundOffset(0),
+                        Length());
+}
+
+int32_t ReadableFontData::CopyTo(ByteArray* ba) {
+  return array_->CopyTo(ba, BoundOffset(0), Length());
+}
+
+int32_t ReadableFontData::SearchUShort(int32_t start_index,
+                                       int32_t start_offset,
+                                       int32_t end_index,
+                                       int32_t end_offset,
+                                       int32_t length,
+                                       int32_t key) {
+  int32_t location = 0;
+  int32_t bottom = 0;
+  int32_t top = length;
+  while (top != bottom) {
+    location = (top + bottom) / 2;
+    int32_t location_start = ReadUShort(start_index + location * start_offset);
+    if (key < location_start) {
+      // location is below current location
+      top = location;
+    } else {
+      // is key below the upper bound?
+      int32_t location_end = ReadUShort(end_index + location * end_offset);
+#if defined (SFNTLY_DEBUG_FONTDATA)
+      fprintf(stderr, "**start: %d; end: %d\n", location_start, location_end);
+#endif
+      if (key <= location_end) {
+        return location;
+      } else {
+        // location is above the current location
+        bottom = location + 1;
+      }
+    }
+  }
+  return -1;
+}
+
+int32_t ReadableFontData::SearchUShort(int32_t start_index,
+                                       int32_t start_offset,
+                                       int32_t length,
+                                       int32_t key) {
+  int32_t location = 0;
+  int32_t bottom = 0;
+  int32_t top = length;
+  while (top != bottom) {
+    location = (top + bottom) / 2;
+    int32_t location_start = ReadUShort(start_index + location * start_offset);
+    if (key < location_start) {
+      // location is below current location
+      top = location;
+    } else if (key > location_start) {
+      // location is above current location
+      bottom = location + 1;
+    } else {
+      return location;
+    }
+  }
+  return -1;
+}
+
+int32_t ReadableFontData::SearchULong(int32_t start_index,
+                                      int32_t start_offset,
+                                      int32_t end_index,
+                                      int32_t end_offset,
+                                      int32_t length,
+                                      int32_t key) {
+  int32_t location = 0;
+  int32_t bottom = 0;
+  int32_t top = length;
+  while (top != bottom) {
+    location = (top + bottom) / 2;
+    int32_t location_start = ReadULongAsInt(start_index
+                                            + location * start_offset);
+    if (key < location_start) {
+      // location is below current location
+      top = location;
+    } else {
+      // is key below the upper bound?
+      int32_t location_end = ReadULongAsInt(end_index + location * end_offset);
+#if defined (SFNTLY_DEBUG_FONTDATA)
+      fprintf(stderr, "**start: %d; end: %d\n", location_start, location_end);
+#endif
+      if (key <= location_end) {
+        return location;
+      } else {
+        // location is above the current location
+        bottom = location + 1;
+      }
+    }
+  }
+  return -1;
+}
+
+CALLER_ATTACH FontData* ReadableFontData::Slice(int32_t offset,
+                                                int32_t length) {
+  if (offset < 0 || offset + length > Size()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException(
+        "Attempt to bind data outside of its limits");
+#endif
+    return NULL;
+  }
+  FontDataPtr slice = new ReadableFontData(this, offset, length);
+  return slice.Detach();
+}
+
+CALLER_ATTACH FontData* ReadableFontData::Slice(int32_t offset) {
+  if (offset < 0 || offset > Size()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException(
+        "Attempt to bind data outside of its limits");
+#endif
+    return NULL;
+  }
+  FontDataPtr slice = new ReadableFontData(this, offset);
+  return slice.Detach();
+}
+
+ReadableFontData::ReadableFontData(ReadableFontData* data, int32_t offset)
+    : FontData(data, offset),
+      checksum_set_(false),
+      checksum_(0) {
+}
+
+ReadableFontData::ReadableFontData(ReadableFontData* data,
+                                   int32_t offset,
+                                   int32_t length)
+    : FontData(data, offset, length),
+      checksum_set_(false),
+      checksum_(0) {
+}
+
+void ReadableFontData::ComputeChecksum() {
+  // TODO(arthurhsu): IMPLEMENT: synchronization/atomicity
+  int64_t sum = 0;
+  if (checksum_range_.empty()) {
+    sum = ComputeCheckSum(0, Length());
+  } else {
+    for (uint32_t low_bound_index = 0; low_bound_index < checksum_range_.size();
+         low_bound_index += 2) {
+      int32_t low_bound = checksum_range_[low_bound_index];
+      int32_t high_bound = (low_bound_index == checksum_range_.size() - 1) ?
+                                Length() :
+                                checksum_range_[low_bound_index + 1];
+      sum += ComputeCheckSum(low_bound, high_bound);
+    }
+  }
+
+  checksum_ = sum & 0xffffffffL;
+  checksum_set_ = true;
+}
+
+int64_t ReadableFontData::ComputeCheckSum(int32_t low_bound,
+                                          int32_t high_bound) {
+  int64_t sum = 0;
+  // Checksum all whole 4-byte chunks.
+  for (int32_t i = low_bound; i <= high_bound - 4; i += 4) {
+    sum += ReadULong(i);
+  }
+
+  // Add last fragment if not 4-byte multiple
+  int32_t off = high_bound & -4;
+  if (off < high_bound) {
+    int32_t b3 = ReadUByte(off);
+    int32_t b2 = (off + 1 < high_bound) ? ReadUByte(off + 1) : 0;
+    int32_t b1 = (off + 2 < high_bound) ? ReadUByte(off + 2) : 0;
+    int32_t b0 = 0;
+    sum += (b3 << 24) | (b2 << 16) | (b1 << 8) | b0;
+  }
+  return sum;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/readable_font_data.h b/sfntly/cpp/src/sfntly/data/readable_font_data.h
new file mode 100644
index 0000000..b43c626
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/readable_font_data.h
@@ -0,0 +1,308 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_READABLE_FONT_DATA_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_READABLE_FONT_DATA_H_
+
+#include "sfntly/data/font_data.h"
+#include "sfntly/port/lock.h"
+
+namespace sfntly {
+
+class WritableFontData;
+class OutputStream;
+
+// Writable font data wrapper. Supports reading of data primitives in the
+// TrueType / OpenType spec.
+// The data types used are as listed:
+// BYTE       8-bit unsigned integer.
+// CHAR       8-bit signed integer.
+// USHORT     16-bit unsigned integer.
+// SHORT      16-bit signed integer.
+// UINT24     24-bit unsigned integer.
+// ULONG      32-bit unsigned integer.
+// LONG       32-bit signed integer.
+// Fixed      32-bit signed fixed-point number (16.16)
+// FUNIT      Smallest measurable distance in the em space.
+// FWORD      16-bit signed integer (SHORT) that describes a quantity in FUnits.
+// UFWORD     16-bit unsigned integer (USHORT) that describes a quantity in
+//            FUnits.
+// F2DOT14    16-bit signed fixed number with the low 14 bits of fraction (2.14)
+// LONGDATETIME  Date represented in number of seconds since 12:00 midnight,
+//               January 1, 1904. The value is represented as a signed 64-bit
+//               integer.
+
+class ReadableFontData : public FontData,
+                         public RefCounted<ReadableFontData> {
+ public:
+  explicit ReadableFontData(ByteArray* array);
+  virtual ~ReadableFontData();
+
+  static CALLER_ATTACH ReadableFontData* CreateReadableFontData(ByteVector* b);
+
+  // Gets a computed checksum for the data. This checksum uses the OpenType spec
+  // calculation. Every ULong value (32 bit unsigned) in the data is summed and
+  // the resulting value is truncated to 32 bits. If the data length in bytes is
+  // not an integral multiple of 4 then any remaining bytes are treated as the
+  // start of a 4 byte sequence whose remaining bytes are zero.
+  // @return the checksum
+  int64_t Checksum();
+
+  // Sets the bounds to use for computing the checksum. These bounds are in
+  // begin and end pairs. If an odd number is given then the final range is
+  // assumed to extend to the end of the data. The lengths of each range must be
+  // a multiple of 4.
+  // @param ranges the range bounds to use for the checksum
+  void SetCheckSumRanges(const IntegerList& ranges);
+
+  // Read the UBYTE at the given index.
+  // @param index index into the font data
+  // @return the UBYTE; -1 if outside the bounds of the font data
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadUByte(int32_t index);
+
+  // Read the BYTE at the given index.
+  // @param index index into the font data
+  // @return the BYTE
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadByte(int32_t index);
+
+  // Read the bytes at the given index into the array.
+  // @param index index into the font data
+  // @param b the destination for the bytes read
+  // @param offset offset in the byte array to place the bytes
+  // @param length the length of bytes to read
+  // @return the number of bytes actually read; -1 if the index is outside the
+  //         bounds of the font data
+  virtual int32_t ReadBytes(int32_t index,
+                            byte_t* b,
+                            int32_t offset,
+                            int32_t length);
+
+  // Read the CHAR at the given index.
+  // @param index index into the font data
+  // @return the CHAR
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadChar(int32_t index);
+
+  // Read the USHORT at the given index.
+  // @param index index into the font data
+  // @return the USHORT
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadUShort(int32_t index);
+
+  // Read the SHORT at the given index.
+  // @param index index into the font data
+  // @return the SHORT
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadShort(int32_t index);
+
+  // Read the UINT24 at the given index.
+  // @param index index into the font data
+  // @return the UINT24
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadUInt24(int32_t index);
+
+  // Read the ULONG at the given index.
+  // @param index index into the font data
+  // @return the ULONG
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int64_t ReadULong(int32_t index);
+
+  // Read the ULONG at the given index as int32_t.
+  // @param index index into the font data
+  // @return the ULONG
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadULongAsInt(int32_t index);
+
+  // Read the ULONG at the given index, little-endian variant
+  // @param index index into the font data
+  // @return the ULONG
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int64_t ReadULongLE(int32_t index);
+
+  // Read the LONG at the given index.
+  // @param index index into the font data
+  // @return the LONG
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadLong(int32_t index);
+
+  // Read the Fixed at the given index.
+  // @param index index into the font data
+  // @return the Fixed
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadFixed(int32_t index);
+
+  // Read the LONGDATETIME at the given index.
+  // @param index index into the font data
+  // @return the LONGDATETIME
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int64_t ReadDateTimeAsLong(int32_t index);
+
+  // Read the FWORD at the given index.
+  // @param index index into the font data
+  // @return the FWORD
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadFWord(int32_t index);
+
+  // Read the UFWORD at the given index.
+  // @param index index into the font data
+  // @return the UFWORD
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t ReadFUFWord(int32_t index);
+
+  // Note: Not ported because they just throw UnsupportedOperationException()
+  //       in Java.
+  /*
+  virtual int32_t ReadFUnit(int32_t index);
+  virtual int64_t ReadF2Dot14(int32_t index);
+  */
+
+  // Copy the FontData to an OutputStream.
+  // @param os the destination
+  // @return number of bytes copied
+  // @throws IOException
+  virtual int32_t CopyTo(OutputStream* os);
+
+  // Copy the FontData to a WritableFontData.
+  // @param wfd the destination
+  // @return number of bytes copied
+  // @throws IOException
+  virtual int32_t CopyTo(WritableFontData* wfd);
+
+  // Make gcc -Woverloaded-virtual happy.
+  virtual int32_t CopyTo(ByteArray* ba);
+
+  // Search for the key value in the range tables provided.
+  // The search looks through the start-end pairs looking for the key value. It
+  // is assumed that the start-end pairs are both represented by UShort values,
+  // ranges do not overlap, and are monotonically increasing.
+  // @param startIndex the position to read the first start value from
+  // @param startOffset the offset between subsequent start values
+  // @param endIndex the position to read the first end value from
+  // @param endOffset the offset between subsequent end values
+  // @param length the number of start-end pairs
+  // @param key the value to search for
+  // @return the index of the start-end pairs in which the key was found; -1
+  //         otherwise
+  int32_t SearchUShort(int32_t start_index,
+                       int32_t start_offset,
+                       int32_t end_index,
+                       int32_t end_offset,
+                       int32_t length,
+                       int32_t key);
+
+  // Search for the key value in the table provided.
+  // The search looks through the values looking for the key value. It is
+  // assumed that the are represented by UShort values and are monotonically
+  // increasing.
+  // @param startIndex the position to read the first start value from
+  // @param startOffset the offset between subsequent start values
+  // @param length the number of start-end pairs
+  // @param key the value to search for
+  // @return the index of the start-end pairs in which the key was found; -1
+  //         otherwise
+  int32_t SearchUShort(int32_t start_index,
+                       int32_t start_offset,
+                       int32_t length,
+                       int32_t key);
+
+  // Search for the key value in the range tables provided.
+  // The search looks through the start-end pairs looking for the key value. It
+  // is assumed that the start-end pairs are both represented by ULong values
+  // that can be represented within 31 bits, ranges do not overlap, and are
+  // monotonically increasing.
+  // @param startIndex the position to read the first start value from
+  // @param startOffset the offset between subsequent start values
+  // @param endIndex the position to read the first end value from
+  // @param endOffset the offset between subsequent end values
+  // @param length the number of start-end pairs
+  // @param key the value to search for
+  // @return the index of the start-end pairs in which the key was found; -1
+  //         otherwise
+  int32_t SearchULong(int32_t start_index,
+                      int32_t start_offset,
+                      int32_t end_index,
+                      int32_t end_offset,
+                      int32_t length,
+                      int32_t key);
+
+
+  // TODO(arthurhsu): IMPLEMENT
+  /*
+  virtual int32_t ReadFUnit(int32_t index);
+  virtual int64_t ReadF2Dot14(int32_t index);
+  virtual int64_t ReadLongDateTime(int32_t index);
+  */
+
+  // Makes a slice of this FontData. The returned slice will share the data with
+  // the original FontData.
+  // @param offset the start of the slice
+  // @param length the number of bytes in the slice
+  // @return a slice of the original FontData
+  // Note: C++ polymorphism requires return type to be consistent
+  virtual CALLER_ATTACH FontData* Slice(int32_t offset, int32_t length);
+
+  // Makes a bottom bound only slice of this array. The returned slice will
+  // share the data with the original FontData.
+  // @param offset the start of the slice
+  // @return a slice of the original FontData
+  // Note: C++ polymorphism requires return type to be consistent
+  virtual CALLER_ATTACH FontData* Slice(int32_t offset);
+
+  // Not Ported: toString()
+
+ protected:
+  // Constructor. Creates a bounded wrapper of another ReadableFontData from the
+  // given offset until the end of the original ReadableFontData.
+  // @param data data to wrap
+  // @param offset the start of this data's view of the original data
+  ReadableFontData(ReadableFontData* data, int32_t offset);
+
+  // Constructor. Creates a bounded wrapper of another ReadableFontData from the
+  // given offset until the end of the original ReadableFontData.
+  // @param data data to wrap
+  // @param offset the start of this data's view of the original data
+  // @param length the length of the other FontData to use
+  ReadableFontData(ReadableFontData* data, int32_t offset, int32_t length);
+
+ private:
+  // Compute the checksum for the font data using any ranges set for the
+  // calculation.
+  void ComputeChecksum();
+
+  // Do the actual computation of the checksum for a range using the
+  // TrueType/OpenType checksum algorithm. The range used is from the low bound
+  // to the high bound in steps of four bytes. If any of the bytes within that 4
+  // byte segment are not readable then it will considered a zero for
+  // calculation.
+  // Only called from within a synchronized method so it does not need to be
+  // synchronized itself.
+  // @param lowBound first position to start a 4 byte segment on
+  // @param highBound last possible position to start a 4 byte segment on
+  // @return the checksum for the total range
+  int64_t ComputeCheckSum(int32_t low_bound, int32_t high_bound);
+
+  Lock checksum_lock_;
+  bool checksum_set_;
+  int64_t checksum_;
+  IntegerList checksum_range_;
+};
+typedef Ptr<ReadableFontData> ReadableFontDataPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_READABLE_FONT_DATA_H_
diff --git a/sfntly/cpp/src/sfntly/data/writable_font_data.cc b/sfntly/cpp/src/sfntly/data/writable_font_data.cc
new file mode 100644
index 0000000..7f6f72f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/writable_font_data.cc
@@ -0,0 +1,201 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/data/writable_font_data.h"
+
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/data/growable_memory_byte_array.h"
+
+namespace sfntly {
+
+WritableFontData::WritableFontData(ByteArray* ba) : ReadableFontData(ba) {
+}
+
+WritableFontData::~WritableFontData() {}
+
+// static
+CALLER_ATTACH
+WritableFontData* WritableFontData::CreateWritableFontData(int32_t length) {
+  ByteArrayPtr ba;
+  if (length > 0) {
+    ba = new MemoryByteArray(length);
+    ba->SetFilledLength(length);
+  } else {
+    ba = new GrowableMemoryByteArray();
+  }
+  WritableFontDataPtr wfd = new WritableFontData(ba);
+  return wfd.Detach();
+}
+
+// TODO(arthurhsu): re-investigate the memory model of this function.  It's
+//                  not too useful without copying, but it's not performance
+//                  savvy to do copying.
+CALLER_ATTACH
+WritableFontData* WritableFontData::CreateWritableFontData(ByteVector* b) {
+  ByteArrayPtr ba = new GrowableMemoryByteArray();
+  ba->Put(0, b);
+  WritableFontDataPtr wfd = new WritableFontData(ba);
+  return wfd.Detach();
+}
+
+int32_t WritableFontData::WriteByte(int32_t index, byte_t b) {
+  array_->Put(BoundOffset(index), b);
+  return 1;
+}
+
+int32_t WritableFontData::WriteBytes(int32_t index,
+                                     byte_t* b,
+                                     int32_t offset,
+                                     int32_t length) {
+  return array_->Put(BoundOffset(index),
+                     b,
+                     offset,
+                     BoundLength(index, length));
+}
+
+int32_t WritableFontData::WriteBytes(int32_t index, ByteVector* b) {
+  assert(b);
+  return WriteBytes(index, &((*b)[0]), 0, b->size());
+}
+
+int32_t WritableFontData::WriteBytesPad(int32_t index,
+                                        ByteVector* b,
+                                        int32_t offset,
+                                        int32_t length,
+                                        byte_t pad) {
+  int32_t written =
+      array_->Put(BoundOffset(index),
+                  &((*b)[0]),
+                  offset,
+                  BoundLength(index,
+                              std::min<int32_t>(length, b->size() - offset)));
+  written += WritePadding(written + index, length - written, pad);
+  return written;
+}
+
+int32_t WritableFontData::WritePadding(int32_t index, int32_t count) {
+  return WritePadding(index, count, (byte_t)0);
+}
+
+int32_t WritableFontData::WritePadding(int32_t index, int32_t count,
+                                       byte_t pad) {
+  for (int32_t i = 0; i < count; ++i) {
+    array_->Put(index + i, pad);
+  }
+  return count;
+}
+
+int32_t WritableFontData::WriteChar(int32_t index, byte_t c) {
+  return WriteByte(index, c);
+}
+
+int32_t WritableFontData::WriteUShort(int32_t index, int32_t us) {
+  WriteByte(index, (byte_t)((us >> 8) & 0xff));
+  WriteByte(index + 1, (byte_t)(us & 0xff));
+  return 2;
+}
+
+int32_t WritableFontData::WriteUShortLE(int32_t index, int32_t us) {
+  WriteByte(index, (byte_t)(us & 0xff));
+  WriteByte(index + 1, (byte_t)((us >> 8) & 0xff));
+  return 2;
+}
+
+int32_t WritableFontData::WriteShort(int32_t index, int32_t s) {
+  return WriteUShort(index, s);
+}
+
+int32_t WritableFontData::WriteUInt24(int32_t index, int32_t ui) {
+  WriteByte(index, (byte_t)((ui >> 16) & 0xff));
+  WriteByte(index + 1, (byte_t)((ui >> 8) & 0xff));
+  WriteByte(index + 2, (byte_t)(ui & 0xff));
+  return 3;
+}
+
+int32_t WritableFontData::WriteULong(int32_t index, int64_t ul) {
+  WriteByte(index, (byte_t)((ul >> 24) & 0xff));
+  WriteByte(index + 1, (byte_t)((ul >> 16) & 0xff));
+  WriteByte(index + 2, (byte_t)((ul >> 8) & 0xff));
+  WriteByte(index + 3, (byte_t)(ul & 0xff));
+  return 4;
+}
+
+int32_t WritableFontData::WriteULongLE(int32_t index, int64_t ul) {
+  WriteByte(index, (byte_t)(ul & 0xff));
+  WriteByte(index + 1, (byte_t)((ul >> 8) & 0xff));
+  WriteByte(index + 2, (byte_t)((ul >> 16) & 0xff));
+  WriteByte(index + 3, (byte_t)((ul >> 24) & 0xff));
+  return 4;
+}
+
+int32_t WritableFontData::WriteLong(int32_t index, int64_t l) {
+  return WriteULong(index, l);
+}
+
+int32_t WritableFontData::WriteFixed(int32_t index, int32_t f) {
+  return WriteLong(index, f);
+}
+
+int32_t WritableFontData::WriteDateTime(int32_t index, int64_t date) {
+  WriteULong(index, (date >> 32) & 0xffffffff);
+  WriteULong(index + 4, date & 0xffffffff);
+  return 8;
+}
+
+void WritableFontData::CopyFrom(InputStream* is, int32_t length) {
+  array_->CopyFrom(is, length);
+}
+
+void WritableFontData::CopyFrom(InputStream* is) {
+  array_->CopyFrom(is);
+}
+
+CALLER_ATTACH FontData* WritableFontData::Slice(int32_t offset,
+                                                int32_t length) {
+  if (offset < 0 || offset + length > Size()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException(
+        "Attempt to bind data outside of its limits");
+#endif
+    return NULL;
+  }
+  FontDataPtr slice = new WritableFontData(this, offset, length);
+  return slice.Detach();
+}
+
+CALLER_ATTACH FontData* WritableFontData::Slice(int32_t offset) {
+  if (offset > Size()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException(
+        "Attempt to bind data outside of its limits");
+#endif
+    return NULL;
+  }
+  FontDataPtr slice = new WritableFontData(this, offset);
+  return slice.Detach();
+}
+
+WritableFontData::WritableFontData(WritableFontData* data, int32_t offset)
+    : ReadableFontData(data, offset) {
+}
+
+WritableFontData::WritableFontData(WritableFontData* data,
+                                   int32_t offset,
+                                   int32_t length)
+    : ReadableFontData(data, offset, length) {
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/data/writable_font_data.h b/sfntly/cpp/src/sfntly/data/writable_font_data.h
new file mode 100644
index 0000000..d2a049e
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/data/writable_font_data.h
@@ -0,0 +1,211 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_DATA_WRITABLE_FONT_DATA_H_
+#define SFNTLY_CPP_SRC_SFNTLY_DATA_WRITABLE_FONT_DATA_H_
+
+#include "sfntly/data/readable_font_data.h"
+
+namespace sfntly {
+
+// Writable font data wrapper. Supports writing of data primitives in the
+// TrueType / OpenType spec.
+class WritableFontData : public ReadableFontData {
+ public:
+  explicit WritableFontData(ByteArray* ba);
+  virtual ~WritableFontData();
+
+  // Constructs a writable font data object. If the length is specified as
+  // positive then a fixed size font data object will be created. If the length
+  // is zero or less then a growable font data object will be created and the
+  // size will be used as an estimate to help in allocating the original space.
+  // @param length if length > 0 create a fixed length font data; otherwise
+  //        create a growable font data
+  // @return a new writable font data
+  static CALLER_ATTACH WritableFontData* CreateWritableFontData(int32_t length);
+
+  // Constructs a writable font data object. The new font data object will wrap
+  // the bytes passed in to the factory and it will take make a copy of those
+  // bytes.
+  // @param b the byte vector to wrap
+  // @return a new writable font data
+  static CALLER_ATTACH WritableFontData* CreateWritableFontData(ByteVector* b);
+
+  // Write a byte at the given index.
+  // @param index index into the font data
+  // @param b the byte to write
+  // @return the number of bytes written
+  virtual int32_t WriteByte(int32_t index, byte_t b);
+
+  // Write the bytes from the array.
+  // @param index index into the font data
+  // @param b the source for the bytes to be written
+  // @param offset offset in the byte array
+  // @param length the length of the bytes to be written
+  // @return the number of bytes actually written; -1 if the index is outside
+  //         the FontData's range
+  virtual int32_t WriteBytes(int32_t index,
+                             byte_t* b,
+                             int32_t offset,
+                             int32_t length);
+
+  // Write the bytes from the array.
+  // @param index index into the font data
+  // @param b the source for the bytes to be written
+  // @return the number of bytes actually written; -1 if the index is outside
+  //         the FontData's range
+  virtual int32_t WriteBytes(int32_t index, ByteVector* b);
+
+  // Write the bytes from the array and pad if necessary.
+  // Write to the length given using the byte array provided and if there are
+  // not enough bytes in the array then pad to the requested length using the
+  // pad byte specified.
+  // @param index index into the font data
+  // @param b the source for the bytes to be written
+  // @param offset offset in the byte array
+  // @param length the length of the bytes to be written
+  // @param pad the padding byte to be used if necessary
+  // @return the number of bytes actually written
+  virtual int32_t WriteBytesPad(int32_t index,
+                                ByteVector* b,
+                                int32_t offset,
+                                int32_t length,
+                                byte_t pad);
+
+  // Writes padding to the FontData. The padding byte written is 0x00.
+  // @param index index into the font data
+  // @param count the number of pad bytes to write
+  // @return the number of pad bytes written
+  virtual int32_t WritePadding(int32_t index, int32_t count);
+
+  // Writes padding to the FontData.
+  // @param index index into the font data
+  // @param count the number of pad bytes to write
+  // @param pad the byte value to use as padding
+  // @return the number of pad bytes written
+  virtual int32_t WritePadding(int32_t index, int32_t count, byte_t pad);
+
+  // Write the CHAR at the given index.
+  // @param index index into the font data
+  // @param c the CHAR
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteChar(int32_t index, byte_t c);
+
+  // Write the USHORT at the given index.
+  // @param index index into the font data
+  // @param us the USHORT
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteUShort(int32_t index, int32_t us);
+
+  // Write the USHORT at the given index in little endian format.
+  // @param index index into the font data
+  // @param us the USHORT
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteUShortLE(int32_t index, int32_t us);
+
+  // Write the SHORT at the given index.
+  // @param index index into the font data
+  // @param s the SHORT
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteShort(int32_t index, int32_t s);
+
+  // Write the UINT24 at the given index.
+  // @param index index into the font data
+  // @param ui the UINT24
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteUInt24(int32_t index, int32_t ui);
+
+  // Write the ULONG at the given index.
+  // @param index index into the font data
+  // @param ul the ULONG
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteULong(int32_t index, int64_t ul);
+
+  // Write the ULONG at the given index in little endian format.
+  // @param index index into the font data
+  // @param ul the ULONG
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteULongLE(int32_t index, int64_t ul);
+
+  // Write the LONG at the given index.
+  // @param index index into the font data
+  // @param l the LONG
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteLong(int32_t index, int64_t l);
+
+  // Write the Fixed at the given index.
+  // @param index index into the font data
+  // @param f the Fixed
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteFixed(int32_t index, int32_t f);
+
+  // Write the LONGDATETIME at the given index.
+  // @param index index into the font data
+  // @param date the LONGDATETIME
+  // @return the number of bytes actually written
+  // @throws IndexOutOfBoundsException if index is outside the FontData's range
+  virtual int32_t WriteDateTime(int32_t index, int64_t date);
+
+  // Copy from the InputStream into this FontData.
+  // @param is the source
+  // @param length the number of bytes to copy
+  // @throws IOException
+  virtual void CopyFrom(InputStream* is, int32_t length);
+
+  // Copy everything from the InputStream into this FontData.
+  // @param is the source
+  // @throws IOException
+  virtual void CopyFrom(InputStream* is);
+
+  // Makes a slice of this FontData. The returned slice will share the data with
+  // the original FontData.
+  // @param offset the start of the slice
+  // @param length the number of bytes in the slice
+  // @return a slice of the original FontData
+  virtual CALLER_ATTACH FontData* Slice(int32_t offset, int32_t length);
+
+  // Makes a bottom bound only slice of this array. The returned slice will
+  // share the data with the original FontData.
+  // @param offset the start of the slice
+  // @return a slice of the original FontData
+  virtual CALLER_ATTACH FontData* Slice(int32_t offset);
+
+ private:
+  // Constructor with a lower bound.
+  // @param data other WritableFontData object to share data with
+  // @param offset offset from the other WritableFontData's data
+  WritableFontData(WritableFontData* data, int32_t offset);
+
+  // Constructor with lower bound and a length bound.
+  // @param data other WritableFontData object to share data with
+  // @param offset offset from the other WritableFontData's data
+  // @param length length of other WritableFontData's data to use
+  WritableFontData(WritableFontData* data, int32_t offset, int32_t length);
+};
+typedef Ptr<WritableFontData> WritableFontDataPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_DATA_WRITABLE_FONT_DATA_H_
diff --git a/sfntly/cpp/src/sfntly/font.cc b/sfntly/cpp/src/sfntly/font.cc
new file mode 100644
index 0000000..347e0c1
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/font.cc
@@ -0,0 +1,557 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/font.h"
+
+#include <stdio.h>
+
+#include <functional>
+#include <algorithm>
+#include <map>
+#include <string>
+#include <typeinfo>
+#include <iterator>
+
+#include "sfntly/data/font_input_stream.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/math/fixed1616.h"
+#include "sfntly/math/font_math.h"
+#include "sfntly/port/exception_type.h"
+#include "sfntly/table/core/font_header_table.h"
+#include "sfntly/table/core/horizontal_device_metrics_table.h"
+#include "sfntly/table/core/horizontal_header_table.h"
+#include "sfntly/table/core/horizontal_metrics_table.h"
+#include "sfntly/table/core/maximum_profile_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+#include "sfntly/tag.h"
+
+namespace sfntly {
+
+const int32_t SFNTVERSION_MAJOR = 1;
+const int32_t SFNTVERSION_MINOR = 0;
+
+/******************************************************************************
+ * Font class
+ ******************************************************************************/
+Font::~Font() {}
+
+bool Font::HasTable(int32_t tag) {
+  TableMap::const_iterator result = tables_.find(tag);
+  TableMap::const_iterator end = tables_.end();
+  return (result != end);
+}
+
+Table* Font::GetTable(int32_t tag) {
+  if (!HasTable(tag)) {
+    return NULL;
+  }
+  return tables_[tag];
+}
+
+const TableMap* Font::GetTableMap() {
+  return &tables_;
+}
+
+void Font::Serialize(OutputStream* os, IntegerList* table_ordering) {
+  assert(table_ordering);
+  IntegerList final_table_ordering;
+  GenerateTableOrdering(table_ordering, &final_table_ordering);
+  TableHeaderList table_records;
+  BuildTableHeadersForSerialization(&final_table_ordering, &table_records);
+
+  FontOutputStream fos(os);
+  SerializeHeader(&fos, &table_records);
+  SerializeTables(&fos, &table_records);
+}
+
+Font::Font(int32_t sfnt_version, ByteVector* digest)
+    : sfnt_version_(sfnt_version) {
+  // non-trivial assignments that makes debugging hard if placed in
+  // initialization list
+  digest_ = *digest;
+}
+
+void Font::BuildTableHeadersForSerialization(IntegerList* table_ordering,
+                                             TableHeaderList* table_headers) {
+  assert(table_headers);
+  assert(table_ordering);
+
+  IntegerList final_table_ordering;
+  GenerateTableOrdering(table_ordering, &final_table_ordering);
+  int32_t table_offset = Offset::kTableRecordBegin + num_tables() *
+                         Offset::kTableRecordSize;
+  for (IntegerList::iterator tag = final_table_ordering.begin(),
+                             tag_end = final_table_ordering.end();
+                             tag != tag_end; ++tag) {
+    if (tables_.find(*tag) == tables_.end()) {
+      continue;
+    }
+    TablePtr table = tables_[*tag];
+    if (table != NULL) {
+      HeaderPtr header =
+          new Header(*tag, table->CalculatedChecksum(), table_offset,
+                     table->header()->length());
+      table_headers->push_back(header);
+      table_offset += (table->DataLength() + 3) & ~3;
+    }
+  }
+}
+
+void Font::SerializeHeader(FontOutputStream* fos,
+                           TableHeaderList* table_headers) {
+  fos->WriteFixed(sfnt_version_);
+  fos->WriteUShort(table_headers->size());
+  int32_t log2_of_max_power_of_2 = FontMath::Log2(table_headers->size());
+  int32_t search_range = 2 << (log2_of_max_power_of_2 - 1 + 4);
+  fos->WriteUShort(search_range);
+  fos->WriteUShort(log2_of_max_power_of_2);
+  fos->WriteUShort((table_headers->size() * 16) - search_range);
+
+  HeaderTagSortedSet sorted_headers;
+  std::copy(table_headers->begin(),
+            table_headers->end(),
+            std::inserter(sorted_headers, sorted_headers.end()));
+
+  for (HeaderTagSortedSet::iterator record = sorted_headers.begin(),
+                                    record_end = sorted_headers.end();
+                                    record != record_end; ++record) {
+    fos->WriteULong((*record)->tag());
+    fos->WriteULong((int32_t)((*record)->checksum()));
+    fos->WriteULong((*record)->offset());
+    fos->WriteULong((*record)->length());
+  }
+}
+
+void Font::SerializeTables(FontOutputStream* fos,
+                           TableHeaderList* table_headers) {
+  assert(fos);
+  assert(table_headers);
+  for (TableHeaderList::iterator record = table_headers->begin(),
+                                 end_of_headers = table_headers->end();
+                                 record != end_of_headers; ++record) {
+    TablePtr target_table = GetTable((*record)->tag());
+    if (target_table == NULL) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IOException("Table out of sync with font header.");
+#endif
+      return;
+    }
+    int32_t table_size = target_table->Serialize(fos);
+    if (table_size != (*record)->length()) {
+      assert(false);
+    }
+    int32_t filler_size = ((table_size + 3) & ~3) - table_size;
+    for (int32_t i = 0; i < filler_size; ++i) {
+      fos->Write(static_cast<byte_t>(0));
+    }
+  }
+}
+
+void Font::GenerateTableOrdering(IntegerList* default_table_ordering,
+                                 IntegerList* table_ordering) {
+  assert(default_table_ordering);
+  assert(table_ordering);
+  table_ordering->clear();
+  if (default_table_ordering->empty()) {
+    DefaultTableOrdering(default_table_ordering);
+  }
+
+  typedef std::map<int32_t, bool> Int2Bool;
+  typedef std::pair<int32_t, bool> Int2BoolEntry;
+  Int2Bool tables_in_font;
+  for (TableMap::iterator table = tables_.begin(), table_end = tables_.end();
+                          table != table_end; ++table) {
+    tables_in_font.insert(Int2BoolEntry(table->first, false));
+  }
+  for (IntegerList::iterator tag = default_table_ordering->begin(),
+                             tag_end = default_table_ordering->end();
+                             tag != tag_end; ++tag) {
+    if (HasTable(*tag)) {
+      table_ordering->push_back(*tag);
+      tables_in_font[*tag] = true;
+    }
+  }
+  for (Int2Bool::iterator table = tables_in_font.begin(),
+                          table_end = tables_in_font.end();
+                          table != table_end; ++table) {
+    if (table->second == false)
+      table_ordering->push_back(table->first);
+  }
+}
+
+void Font::DefaultTableOrdering(IntegerList* default_table_ordering) {
+  assert(default_table_ordering);
+  default_table_ordering->clear();
+  if (HasTable(Tag::CFF)) {
+    default_table_ordering->resize(CFF_TABLE_ORDERING_SIZE);
+    std::copy(CFF_TABLE_ORDERING, CFF_TABLE_ORDERING + CFF_TABLE_ORDERING_SIZE,
+              default_table_ordering->begin());
+    return;
+  }
+  default_table_ordering->resize(TRUE_TYPE_TABLE_ORDERING_SIZE);
+  std::copy(TRUE_TYPE_TABLE_ORDERING,
+            TRUE_TYPE_TABLE_ORDERING + TRUE_TYPE_TABLE_ORDERING_SIZE,
+            default_table_ordering->begin());
+}
+
+/******************************************************************************
+ * Font::Builder class
+ ******************************************************************************/
+Font::Builder::~Builder() {}
+
+CALLER_ATTACH Font::Builder* Font::Builder::GetOTFBuilder(FontFactory* factory,
+                                                          InputStream* is) {
+  FontBuilderPtr builder = new Builder(factory);
+  builder->LoadFont(is);
+  return builder.Detach();
+}
+
+CALLER_ATTACH Font::Builder* Font::Builder::GetOTFBuilder(
+    FontFactory* factory,
+    WritableFontData* wfd,
+    int32_t offset_to_offset_table) {
+  FontBuilderPtr builder = new Builder(factory);
+  builder->LoadFont(wfd, offset_to_offset_table);
+  return builder.Detach();
+}
+
+CALLER_ATTACH Font::Builder* Font::Builder::GetOTFBuilder(
+    FontFactory* factory) {
+  FontBuilderPtr builder = new Builder(factory);
+  return builder.Detach();
+}
+
+bool Font::Builder::ReadyToBuild() {
+  // just read in data with no manipulation
+  if (table_builders_.empty() && !data_blocks_.empty()) {
+    return true;
+  }
+
+  // TODO(stuartg): font level checks - required tables etc?
+  for (TableBuilderMap::iterator table_builder = table_builders_.begin(),
+                                 table_builder_end = table_builders_.end();
+                                 table_builder != table_builder_end;
+                                 ++table_builder) {
+    if (!table_builder->second->ReadyToBuild())
+      return false;
+  }
+  return true;
+}
+
+CALLER_ATTACH Font* Font::Builder::Build() {
+  FontPtr font = new Font(sfnt_version_, &digest_);
+
+  if (!table_builders_.empty()) {
+    // Note: Different from Java. Directly use font->tables_ here to avoid
+    //       STL container copying.
+    BuildTablesFromBuilders(font, &table_builders_, &font->tables_);
+  }
+
+  table_builders_.clear();
+  data_blocks_.clear();
+  return font.Detach();
+}
+
+void Font::Builder::SetDigest(ByteVector* digest) {
+  digest_.clear();
+  digest_ = *digest;
+}
+
+void Font::Builder::ClearTableBuilders() {
+  table_builders_.clear();
+}
+
+bool Font::Builder::HasTableBuilder(int32_t tag) {
+  return (table_builders_.find(tag) != table_builders_.end());
+}
+
+Table::Builder* Font::Builder::GetTableBuilder(int32_t tag) {
+  if (HasTableBuilder(tag))
+    return table_builders_[tag];
+  return NULL;
+}
+
+Table::Builder* Font::Builder::NewTableBuilder(int32_t tag) {
+  HeaderPtr header = new Header(tag);
+  TableBuilderPtr builder;
+  builder.Attach(Table::Builder::GetBuilder(header, NULL));
+  table_builders_.insert(TableBuilderEntry(header->tag(), builder));
+  return builder;
+}
+
+Table::Builder* Font::Builder::NewTableBuilder(int32_t tag,
+                                               ReadableFontData* src_data) {
+  assert(src_data);
+  WritableFontDataPtr data;
+  data.Attach(WritableFontData::CreateWritableFontData(src_data->Length()));
+  // TODO(stuarg): take over original data instead?
+  src_data->CopyTo(data);
+
+  HeaderPtr header = new Header(tag, data->Length());
+  TableBuilderPtr builder;
+  builder.Attach(Table::Builder::GetBuilder(header, data));
+  table_builders_.insert(TableBuilderEntry(tag, builder));
+  return builder;
+}
+
+void Font::Builder::RemoveTableBuilder(int32_t tag) {
+  TableBuilderMap::iterator target = table_builders_.find(tag);
+  if (target != table_builders_.end()) {
+    table_builders_.erase(target);
+  }
+}
+
+Font::Builder::Builder(FontFactory* factory)
+    : factory_(factory),
+      sfnt_version_(Fixed1616::Fixed(SFNTVERSION_MAJOR, SFNTVERSION_MINOR)) {
+}
+
+void Font::Builder::LoadFont(InputStream* is) {
+  // Note: we do not throw exception here for is.  This is more of an assertion.
+  assert(is);
+  FontInputStream font_is(is);
+  HeaderOffsetSortedSet records;
+  ReadHeader(&font_is, &records);
+  LoadTableData(&records, &font_is, &data_blocks_);
+  BuildAllTableBuilders(&data_blocks_, &table_builders_);
+  font_is.Close();
+}
+
+void Font::Builder::LoadFont(WritableFontData* wfd,
+                             int32_t offset_to_offset_table) {
+  // Note: we do not throw exception here for is.  This is more of an assertion.
+  assert(wfd);
+  HeaderOffsetSortedSet records;
+  ReadHeader(wfd, offset_to_offset_table, &records);
+  LoadTableData(&records, wfd, &data_blocks_);
+  BuildAllTableBuilders(&data_blocks_, &table_builders_);
+}
+
+int32_t Font::Builder::SfntWrapperSize() {
+  return Offset::kSfntHeaderSize +
+         (Offset::kTableRecordSize * table_builders_.size());
+}
+
+void Font::Builder::BuildAllTableBuilders(DataBlockMap* table_data,
+                                          TableBuilderMap* builder_map) {
+  for (DataBlockMap::iterator record = table_data->begin(),
+                              record_end = table_data->end();
+                              record != record_end; ++record) {
+    TableBuilderPtr builder;
+    builder.Attach(GetTableBuilder(record->first.p_, record->second.p_));
+    builder_map->insert(TableBuilderEntry(record->first->tag(), builder));
+  }
+  InterRelateBuilders(&table_builders_);
+}
+
+CALLER_ATTACH
+Table::Builder* Font::Builder::GetTableBuilder(Header* header,
+                                               WritableFontData* data) {
+  return Table::Builder::GetBuilder(header, data);
+}
+
+void Font::Builder::BuildTablesFromBuilders(Font* font,
+                                            TableBuilderMap* builder_map,
+                                            TableMap* table_map) {
+  UNREFERENCED_PARAMETER(font);
+  InterRelateBuilders(builder_map);
+
+  // Now build all the tables.
+  for (TableBuilderMap::iterator builder = builder_map->begin(),
+                                 builder_end = builder_map->end();
+                                 builder != builder_end; ++builder) {
+    TablePtr table;
+    if (builder->second && builder->second->ReadyToBuild()) {
+      table.Attach(down_cast<Table*>(builder->second->Build()));
+    }
+    if (table == NULL) {
+      table_map->clear();
+#if !defined (SFNTLY_NO_EXCEPTION)
+      std::string builder_string = "Unable to build table - ";
+      char* table_name = TagToString(builder->first);
+      builder_string += table_name;
+      delete[] table_name;
+      throw RuntimeException(builder_string.c_str());
+#endif
+      return;
+    }
+    table_map->insert(TableMapEntry(table->header()->tag(), table));
+  }
+}
+
+static Table::Builder* GetBuilder(TableBuilderMap* builder_map, int32_t tag) {
+  if (builder_map) {
+    TableBuilderMap::iterator target = builder_map->find(tag);
+    if (target != builder_map->end()) {
+      return target->second.p_;
+    }
+  }
+
+  return NULL;
+}
+
+void Font::Builder::InterRelateBuilders(TableBuilderMap* builder_map) {
+  Table::Builder* raw_head_builder = GetBuilder(builder_map, Tag::head);
+  FontHeaderTableBuilderPtr header_table_builder;
+  if (raw_head_builder != NULL) {
+      header_table_builder =
+          down_cast<FontHeaderTable::Builder*>(raw_head_builder);
+  }
+
+  Table::Builder* raw_hhea_builder = GetBuilder(builder_map, Tag::hhea);
+  HorizontalHeaderTableBuilderPtr horizontal_header_builder;
+  if (raw_head_builder != NULL) {
+      horizontal_header_builder =
+          down_cast<HorizontalHeaderTable::Builder*>(raw_hhea_builder);
+  }
+
+  Table::Builder* raw_maxp_builder = GetBuilder(builder_map, Tag::maxp);
+  MaximumProfileTableBuilderPtr max_profile_builder;
+  if (raw_maxp_builder != NULL) {
+      max_profile_builder =
+          down_cast<MaximumProfileTable::Builder*>(raw_maxp_builder);
+  }
+
+  Table::Builder* raw_loca_builder = GetBuilder(builder_map, Tag::loca);
+  LocaTableBuilderPtr loca_table_builder;
+  if (raw_loca_builder != NULL) {
+      loca_table_builder = down_cast<LocaTable::Builder*>(raw_loca_builder);
+  }
+
+  Table::Builder* raw_hmtx_builder = GetBuilder(builder_map, Tag::hmtx);
+  HorizontalMetricsTableBuilderPtr horizontal_metrics_builder;
+  if (raw_hmtx_builder != NULL) {
+      horizontal_metrics_builder =
+          down_cast<HorizontalMetricsTable::Builder*>(raw_hmtx_builder);
+  }
+
+#if defined (SFNTLY_EXPERIMENTAL)
+  Table::Builder* raw_hdmx_builder = GetBuilder(builder_map, Tag::hdmx);
+  HorizontalDeviceMetricsTableBuilderPtr hdmx_table_builder;
+  if (raw_hdmx_builder != NULL) {
+      hdmx_table_builder =
+          down_cast<HorizontalDeviceMetricsTable::Builder*>(raw_hdmx_builder);
+  }
+#endif
+
+  // set the inter table data required to build certain tables
+  if (horizontal_metrics_builder != NULL) {
+    if (max_profile_builder != NULL) {
+      horizontal_metrics_builder->SetNumGlyphs(
+          max_profile_builder->NumGlyphs());
+    }
+    if (horizontal_header_builder != NULL) {
+      horizontal_metrics_builder->SetNumberOfHMetrics(
+          horizontal_header_builder->NumberOfHMetrics());
+    }
+  }
+
+  if (loca_table_builder != NULL) {
+    if (max_profile_builder != NULL) {
+      loca_table_builder->SetNumGlyphs(max_profile_builder->NumGlyphs());
+    }
+    if (header_table_builder != NULL) {
+      loca_table_builder->set_format_version(
+          header_table_builder->IndexToLocFormat());
+    }
+  }
+
+#if defined (SFNTLY_EXPERIMENTAL)
+  // Note: In C++, hdmx_table_builder can be NULL in a subsetter.
+  if (max_profile_builder != NULL && hdmx_table_builder != NULL) {
+    hdmx_table_builder->SetNumGlyphs(max_profile_builder->NumGlyphs());
+  }
+#endif
+}
+
+void Font::Builder::ReadHeader(FontInputStream* is,
+                               HeaderOffsetSortedSet* records) {
+  assert(records);
+  sfnt_version_ = is->ReadFixed();
+  num_tables_ = is->ReadUShort();
+  search_range_ = is->ReadUShort();
+  entry_selector_ = is->ReadUShort();
+  range_shift_ = is->ReadUShort();
+
+  for (int32_t table_number = 0; table_number < num_tables_; ++table_number) {
+    // Need to use temporary vars here.  C++ evaluates function parameters from
+    // right to left and thus breaks the order of input stream.
+    int32_t tag = is->ReadULongAsInt();
+    int64_t checksum = is->ReadULong();
+    int32_t offset = is->ReadULongAsInt();
+    int32_t length = is->ReadULongAsInt();
+    HeaderPtr table = new Header(tag, checksum, offset, length);
+    records->insert(table);
+  }
+}
+
+void Font::Builder::ReadHeader(ReadableFontData* fd,
+                               int32_t offset,
+                               HeaderOffsetSortedSet* records) {
+  assert(records);
+  sfnt_version_ = fd->ReadFixed(offset + Offset::kSfntVersion);
+  num_tables_ = fd->ReadUShort(offset + Offset::kNumTables);
+  search_range_ = fd->ReadUShort(offset + Offset::kSearchRange);
+  entry_selector_ = fd->ReadUShort(offset + Offset::kEntrySelector);
+  range_shift_ = fd->ReadUShort(offset + Offset::kRangeShift);
+
+  int32_t table_offset = offset + Offset::kTableRecordBegin;
+  for (int32_t table_number = 0;
+       table_number < num_tables_;
+       table_number++, table_offset += Offset::kTableRecordSize) {
+    int32_t tag = fd->ReadULongAsInt(table_offset + Offset::kTableTag);
+    int64_t checksum = fd->ReadULong(table_offset + Offset::kTableCheckSum);
+    int32_t offset = fd->ReadULongAsInt(table_offset + Offset::kTableOffset);
+    int32_t length = fd->ReadULongAsInt(table_offset + Offset::kTableLength);
+    HeaderPtr table = new Header(tag, checksum, offset, length);
+    records->insert(table);
+  }
+}
+
+void Font::Builder::LoadTableData(HeaderOffsetSortedSet* headers,
+                                  FontInputStream* is,
+                                  DataBlockMap* table_data) {
+  assert(table_data);
+  for (HeaderOffsetSortedSet::iterator table_header = headers->begin(),
+                                       table_end = headers->end();
+                                       table_header != table_end;
+                                       ++table_header) {
+    is->Skip((*table_header)->offset() - is->position());
+    FontInputStream table_is(is, (*table_header)->length());
+    WritableFontDataPtr data;
+    data.Attach(
+        WritableFontData::CreateWritableFontData((*table_header)->length()));
+    data->CopyFrom(&table_is, (*table_header)->length());
+    table_data->insert(DataBlockEntry(*table_header, data));
+  }
+}
+
+void Font::Builder::LoadTableData(HeaderOffsetSortedSet* headers,
+                                  WritableFontData* fd,
+                                  DataBlockMap* table_data) {
+  for (HeaderOffsetSortedSet::iterator table_header = headers->begin(),
+                                       table_end = headers->end();
+                                       table_header != table_end;
+                                       ++table_header) {
+    FontDataPtr sliced_data;
+    sliced_data.Attach(
+        fd->Slice((*table_header)->offset(), (*table_header)->length()));
+    WritableFontDataPtr data = down_cast<WritableFontData*>(sliced_data.p_);
+    table_data->insert(DataBlockEntry(*table_header, data));
+  }
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/font.h b/sfntly/cpp/src/sfntly/font.h
new file mode 100644
index 0000000..975e8cc
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/font.h
@@ -0,0 +1,352 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_FONT_H_
+#define SFNTLY_CPP_SRC_SFNTLY_FONT_H_
+
+#include <vector>
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/port/type.h"
+#include "sfntly/port/endian.h"
+#include "sfntly/data/font_input_stream.h"
+#include "sfntly/data/font_output_stream.h"
+#include "sfntly/data/writable_font_data.h"
+#include "sfntly/table/table.h"
+
+namespace sfntly {
+
+// Note: following constants are embedded in Font class in Java.  They are
+//       extracted out for easier reference from other classes.  Offset is the
+//       one that is kept within class.
+// Platform ids. These are used in a number of places within the font whenever
+// the platform needs to be specified.
+struct PlatformId {
+  enum {
+    kUnknown = -1,
+    kUnicode = 0,
+    kMacintosh = 1,
+    kISO = 2,
+    kWindows = 3,
+    kCustom = 4
+  };
+};
+
+// Unicode encoding ids. These are used in a number of places within the font
+// whenever character encodings need to be specified.
+struct UnicodeEncodingId {
+  enum {
+    kUnknown = -1,
+    kUnicode1_0 = 0,
+    kUnicode1_1 = 1,
+    kISO10646 = 2,
+    kUnicode2_0_BMP = 3,
+    kUnicode2_0 = 4,
+    kUnicodeVariationSequences = 5
+  };
+};
+
+// Windows encoding ids. These are used in a number of places within the font
+// whenever character encodings need to be specified.
+struct WindowsEncodingId {
+  enum {
+    kUnknown = 0xffffffff,
+    kSymbol = 0,
+    kUnicodeUCS2 = 1,
+    kShiftJIS = 2,
+    kPRC = 3,
+    kBig5 = 4,
+    kWansung = 5,
+    kJohab = 6,
+    kUnicodeUCS4 = 10
+  };
+};
+
+// Macintosh encoding ids. These are used in a number of places within the
+// font whenever character encodings need to be specified.
+struct MacintoshEncodingId {
+  // Macintosh Platform Encodings
+  enum {
+    kUnknown = -1,
+    kRoman = 0,
+    kJapanese = 1,
+    kChineseTraditional = 2,
+    kKorean = 3,
+    kArabic = 4,
+    kHebrew = 5,
+    kGreek = 6,
+    kRussian = 7,
+    kRSymbol = 8,
+    kDevanagari = 9,
+    kGurmukhi = 10,
+    kGujarati = 11,
+    kOriya = 12,
+    kBengali = 13,
+    kTamil = 14,
+    kTelugu = 15,
+    kKannada = 16,
+    kMalayalam = 17,
+    kSinhalese = 18,
+    kBurmese = 19,
+    kKhmer = 20,
+    kThai = 21,
+    kLaotian = 22,
+    kGeorgian = 23,
+    kArmenian = 24,
+    kChineseSimplified = 25,
+    kTibetan = 26,
+    kMongolian = 27,
+    kGeez = 28,
+    kSlavic = 29,
+    kVietnamese = 30,
+    kSindhi = 31,
+    kUninterpreted = 32
+  };
+};
+
+class FontFactory;
+
+// An sfnt container font object. This object is immutable and thread safe. To
+// construct one use an instance of Font::Builder.
+class Font : public RefCounted<Font> {
+ public:
+  // A builder for a font object. The builder allows the for the creation of
+  // immutable Font objects. The builder is a one use non-thread safe object and
+  // once the Font object has been created it is no longer usable. To create a
+  // further Font object new builder will be required.
+  class Builder : public RefCounted<Builder> {
+   public:
+    virtual ~Builder();
+
+    static CALLER_ATTACH Builder*
+        GetOTFBuilder(FontFactory* factory, InputStream* is);
+    static CALLER_ATTACH Builder*
+        GetOTFBuilder(FontFactory* factory,
+                      WritableFontData* ba,
+                      int32_t offset_to_offset_table);
+    static CALLER_ATTACH Builder* GetOTFBuilder(FontFactory* factory);
+
+    // Get the font factory that created this font builder.
+    FontFactory* GetFontFactory() { return factory_; }
+
+    // Is the font ready to build?
+    bool ReadyToBuild();
+
+    // Build the Font. After this call this builder will no longer be usable.
+    CALLER_ATTACH Font* Build();
+
+    // Set a unique fingerprint for the font object.
+    void SetDigest(ByteVector* digest);
+
+    // Clear all table builders.
+    void ClearTableBuilders();
+
+    // Does this font builder have the specified table builder.
+    bool HasTableBuilder(int32_t tag);
+
+    // Get the table builder for the given tag. If there is no builder for that
+    // tag then return a null.
+    Table::Builder* GetTableBuilder(int32_t tag);
+
+    // Creates a new table builder for the table type given by the table id tag.
+    // This new table has been added to the font and will replace any existing
+    // builder for that table.
+    // @return new empty table of the type specified by tag; if tag is not known
+    //         then a generic OpenTypeTable is returned
+    virtual Table::Builder* NewTableBuilder(int32_t tag);
+
+    // Creates a new table builder for the table type given by the table id tag.
+    // It makes a copy of the data provided and uses that copy for the table.
+    // This new table has been added to the font and will replace any existing
+    // builder for that table.
+    virtual Table::Builder* NewTableBuilder(int32_t tag,
+                                            ReadableFontData* src_data);
+
+    // Get a map of the table builders in this font builder accessed by table
+    // tag.
+    virtual TableBuilderMap* table_builders() { return &table_builders_; }
+
+    // Remove the specified table builder from the font builder.
+    // Note: different from Java: we don't return object in removeTableBuilder
+    virtual void RemoveTableBuilder(int32_t tag);
+
+    // Get the number of table builders in the font builder.
+    virtual int32_t number_of_table_builders() {
+      return (int32_t)table_builders_.size();
+    }
+
+   private:
+    explicit Builder(FontFactory* factory);
+    virtual void LoadFont(InputStream* is);
+    virtual void LoadFont(WritableFontData* wfd,
+                          int32_t offset_to_offset_table);
+    int32_t SfntWrapperSize();
+    void BuildAllTableBuilders(DataBlockMap* table_data,
+                               TableBuilderMap* builder_map);
+    CALLER_ATTACH Table::Builder*
+        GetTableBuilder(Header* header, WritableFontData* data);
+    void BuildTablesFromBuilders(Font* font,
+                                 TableBuilderMap* builder_map,
+                                 TableMap* tables);
+    static void InterRelateBuilders(TableBuilderMap* builder_map);
+
+    void ReadHeader(FontInputStream* is,
+                    HeaderOffsetSortedSet* records);
+
+    void ReadHeader(ReadableFontData* fd,
+                    int32_t offset,
+                    HeaderOffsetSortedSet* records);
+
+    void LoadTableData(HeaderOffsetSortedSet* headers,
+                       FontInputStream* is,
+                       DataBlockMap* table_data);
+
+    void LoadTableData(HeaderOffsetSortedSet* headers,
+                       WritableFontData* fd,
+                       DataBlockMap* table_data);
+
+    TableBuilderMap table_builders_;
+    FontFactory* factory_;  // dumb pointer, avoid circular refcounting
+    int32_t sfnt_version_;
+    int32_t num_tables_;
+    int32_t search_range_;
+    int32_t entry_selector_;
+    int32_t range_shift_;
+    DataBlockMap data_blocks_;
+    ByteVector digest_;
+  };
+
+  virtual ~Font();
+
+  // Gets the sfnt version set in the sfnt wrapper of the font.
+  int32_t sfnt_version() { return sfnt_version_; }
+
+  // Gets a copy of the fonts digest that was created when the font was read. If
+  // no digest was set at creation time then the return result will be null.
+  ByteVector* digest() { return &digest_; }
+
+  // Get the checksum for this font.
+  int64_t checksum() { return checksum_; }
+
+  // Get the number of tables in this font.
+  int32_t num_tables() { return (int32_t)tables_.size(); }
+
+  // Whether the font has a particular table.
+  bool HasTable(int32_t tag);
+
+  // UNIMPLEMENTED: public Iterator<? extends Table> iterator
+
+  // Get the table in this font with the specified id.
+  // @param tag the identifier of the table
+  // @return the table specified if it exists; null otherwise
+  // C++ port: rename table() to GetTable()
+  Table* GetTable(int32_t tag);
+
+  // Get a map of the tables in this font accessed by table tag.
+  // @return an unmodifiable view of the tables in this font
+  // Note: renamed tableMap() to GetTableMap()
+  const TableMap* GetTableMap();
+
+  // UNIMPLEMENTED: toString()
+
+  // Serialize the font to the output stream.
+  // @param os the destination for the font serialization
+  // @param tableOrdering the table ordering to apply
+  void Serialize(OutputStream* os, IntegerList* table_ordering);
+
+ private:
+  // Offsets to specific elements in the underlying data. These offsets are
+  // relative to the start of the table or the start of sub-blocks within the
+  // table.
+  struct Offset {
+    enum {
+      // Offsets within the main directory
+      kSfntVersion = 0,
+      kNumTables = 4,
+      kSearchRange = 6,
+      kEntrySelector = 8,
+      kRangeShift = 10,
+      kTableRecordBegin = 12,
+      kSfntHeaderSize = 12,
+
+      // Offsets within a specific table record
+      kTableTag = 0,
+      kTableCheckSum = 4,
+      kTableOffset = 8,
+      kTableLength = 12,
+      kTableRecordSize = 16
+    };
+  };
+
+  // Note: the two constants are moved to tag.h to avoid VC++ bug.
+//  static const int32_t CFF_TABLE_ORDERING[];
+//  static const int32_t TRUE_TYPE_TABLE_ORDERING[];
+
+  // Constructor.
+  // @param sfntVersion the sfnt version
+  // @param digest the computed digest for the font; null if digest was not
+  //        computed
+  // Note: Current C++ port does not support SHA digest validation.
+  Font(int32_t sfnt_version, ByteVector* digest);
+
+  // Build the table headers to be used for serialization. These headers will be
+  // filled out with the data required for serialization. The headers will be
+  // sorted in the order specified and only those specified will have headers
+  // generated.
+  // @param tableOrdering the tables to generate headers for and the order to
+  //        sort them
+  // @return a list of table headers ready for serialization
+  void BuildTableHeadersForSerialization(IntegerList* table_ordering,
+                                         TableHeaderList* table_headers);
+
+  // Searialize the headers.
+  // @param fos the destination stream for the headers
+  // @param tableHeaders the headers to serialize
+  // @throws IOException
+  void SerializeHeader(FontOutputStream* fos, TableHeaderList* table_headers);
+
+  // Serialize the tables.
+  // @param fos the destination stream for the headers
+  // @param tableHeaders the headers for the tables to serialize
+  // @throws IOException
+  void SerializeTables(FontOutputStream* fos, TableHeaderList* table_headers);
+
+  // Generate the full table ordering to used for serialization. The full
+  // ordering uses the partial ordering as a seed and then adds all remaining
+  // tables in the font in an undefined order.
+  // @param defaultTableOrdering the partial ordering to be used as a seed for
+  //        the full ordering
+  // @param (out) table_ordering the full ordering for serialization
+  void GenerateTableOrdering(IntegerList* default_table_ordering,
+                             IntegerList* table_ordering);
+
+  // Get the default table ordering based on the type of the font.
+  // @param (out) default_table_ordering the default table ordering
+  void DefaultTableOrdering(IntegerList* default_table_ordering);
+
+  int32_t sfnt_version_;
+  ByteVector digest_;
+  int64_t checksum_;
+  TableMap tables_;
+};
+typedef Ptr<Font> FontPtr;
+typedef std::vector<FontPtr> FontArray;
+typedef Ptr<Font::Builder> FontBuilderPtr;
+typedef std::vector<FontBuilderPtr> FontBuilderArray;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_FONT_H_
diff --git a/sfntly/cpp/src/sfntly/font_factory.cc b/sfntly/cpp/src/sfntly/font_factory.cc
new file mode 100644
index 0000000..c162a77
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/font_factory.cc
@@ -0,0 +1,214 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/font_factory.h"
+
+#include <string.h>
+
+#include "sfntly/tag.h"
+
+namespace sfntly {
+
+FontFactory::~FontFactory() {
+}
+
+CALLER_ATTACH FontFactory* FontFactory::GetInstance() {
+  FontFactoryPtr instance = new FontFactory();
+  return instance.Detach();
+}
+
+void FontFactory::FingerprintFont(bool fingerprint) {
+  fingerprint_ = fingerprint;
+}
+
+bool FontFactory::FingerprintFont() {
+  return fingerprint_;
+}
+
+void FontFactory::LoadFonts(InputStream* is, FontArray* output) {
+  assert(output);
+  PushbackInputStream* pbis = down_cast<PushbackInputStream*>(is);
+  if (IsCollection(pbis)) {
+    LoadCollection(pbis, output);
+    return;
+  }
+  FontPtr font;
+  font.Attach(LoadSingleOTF(pbis));
+  if (font) {
+    output->push_back(font);
+  }
+}
+
+void FontFactory::LoadFonts(ByteVector* b, FontArray* output) {
+  WritableFontDataPtr wfd;
+  wfd.Attach(WritableFontData::CreateWritableFontData(b));
+  if (IsCollection(wfd)) {
+    LoadCollection(wfd, output);
+    return;
+  }
+  FontPtr font;
+  font.Attach(LoadSingleOTF(wfd));
+  if (font) {
+    output->push_back(font);
+  }
+}
+
+void FontFactory::LoadFontsForBuilding(InputStream* is,
+                                       FontBuilderArray* output) {
+  PushbackInputStream* pbis = down_cast<PushbackInputStream*>(is);
+  if (IsCollection(pbis)) {
+    LoadCollectionForBuilding(pbis, output);
+    return;
+  }
+  FontBuilderPtr builder;
+  builder.Attach(LoadSingleOTFForBuilding(pbis));
+  if (builder) {
+    output->push_back(builder);
+  }
+}
+
+void FontFactory::LoadFontsForBuilding(ByteVector* b,
+                                       FontBuilderArray* output) {
+  WritableFontDataPtr wfd;
+  wfd.Attach(WritableFontData::CreateWritableFontData(b));
+  if (IsCollection(wfd)) {
+    LoadCollectionForBuilding(wfd, output);
+    return;
+  }
+  FontBuilderPtr builder;
+  builder.Attach(LoadSingleOTFForBuilding(wfd, 0));
+  if (builder) {
+    output->push_back(builder);
+  }
+}
+
+void FontFactory::SerializeFont(Font* font, OutputStream* os) {
+  font->Serialize(os, &table_ordering_);
+}
+
+void FontFactory::SetSerializationTableOrdering(
+    const IntegerList& table_ordering) {
+  table_ordering_ = table_ordering;
+}
+
+CALLER_ATTACH Font::Builder* FontFactory::NewFontBuilder() {
+  return Font::Builder::GetOTFBuilder(this);
+}
+
+CALLER_ATTACH Font* FontFactory::LoadSingleOTF(InputStream* is) {
+  FontBuilderPtr builder;
+  builder.Attach(LoadSingleOTFForBuilding(is));
+  return builder->Build();
+}
+
+CALLER_ATTACH Font* FontFactory::LoadSingleOTF(WritableFontData* wfd) {
+  FontBuilderPtr builder;
+  builder.Attach(LoadSingleOTFForBuilding(wfd, 0));
+  return builder->Build();
+}
+
+void FontFactory::LoadCollection(InputStream* is, FontArray* output) {
+  FontBuilderArray ba;
+  LoadCollectionForBuilding(is, &ba);
+  output->reserve(ba.size());
+  for (FontBuilderArray::iterator builder = ba.begin(), builders_end = ba.end();
+                                  builder != builders_end; ++builder) {
+      FontPtr font;
+      font.Attach((*builder)->Build());
+      output->push_back(font);
+  }
+}
+
+void FontFactory::LoadCollection(WritableFontData* wfd, FontArray* output) {
+  FontBuilderArray builders;
+  LoadCollectionForBuilding(wfd, &builders);
+  output->reserve(builders.size());
+  for (FontBuilderArray::iterator builder = builders.begin(),
+                                  builders_end = builders.end();
+                                  builder != builders_end; ++builder) {
+    FontPtr font;
+    font.Attach((*builder)->Build());
+    output->push_back(font);
+  }
+}
+
+CALLER_ATTACH
+Font::Builder* FontFactory::LoadSingleOTFForBuilding(InputStream* is) {
+  // UNIMPLEMENTED: SHA-1 hash checking via Java DigestStream
+  Font::Builder* builder = Font::Builder::GetOTFBuilder(this, is);
+  // UNIMPLEMENTED: setDigest
+  return builder;
+}
+
+CALLER_ATTACH Font::Builder*
+    FontFactory::LoadSingleOTFForBuilding(WritableFontData* wfd,
+                                          int32_t offset_to_offset_table) {
+  // UNIMPLEMENTED: SHA-1 hash checking via Java DigestStream
+  Font::Builder* builder =
+      Font::Builder::GetOTFBuilder(this, wfd, offset_to_offset_table);
+  // UNIMPLEMENTED: setDigest
+  return builder;
+}
+
+void FontFactory::LoadCollectionForBuilding(InputStream* is,
+                                            FontBuilderArray* builders) {
+  assert(is);
+  assert(builders);
+  WritableFontDataPtr wfd;
+  wfd.Attach(WritableFontData::CreateWritableFontData(is->Available()));
+  wfd->CopyFrom(is);
+  LoadCollectionForBuilding(wfd, builders);
+}
+
+void FontFactory::LoadCollectionForBuilding(WritableFontData* wfd,
+                                            FontBuilderArray* builders) {
+  int32_t ttc_tag = wfd->ReadULongAsInt(Offset::kTTCTag);
+  UNREFERENCED_PARAMETER(ttc_tag);
+  int32_t version = wfd->ReadFixed(Offset::kVersion);
+  UNREFERENCED_PARAMETER(version);
+  int32_t num_fonts = wfd->ReadULongAsInt(Offset::kNumFonts);
+
+  builders->reserve(num_fonts);
+  int32_t offset_table_offset = Offset::kOffsetTable;
+  for (int32_t font_number = 0;
+               font_number < num_fonts;
+               font_number++, offset_table_offset += DataSize::kULONG) {
+    int32_t offset = wfd->ReadULongAsInt(offset_table_offset);
+    FontBuilderPtr builder;
+    builder.Attach(LoadSingleOTFForBuilding(wfd, offset));
+    builders->push_back(builder);
+  }
+}
+
+bool FontFactory::IsCollection(PushbackInputStream* pbis) {
+  ByteVector tag(4);
+  pbis->Read(&tag);
+  pbis->Unread(&tag);
+  return Tag::ttcf == GenerateTag(tag[0], tag[1], tag[2], tag[3]);
+}
+
+bool FontFactory::IsCollection(ReadableFontData* rfd) {
+  ByteVector tag(4);
+  rfd->ReadBytes(0, &(tag[0]), 0, tag.size());
+  return Tag::ttcf ==
+         GenerateTag(tag[0], tag[1], tag[2], tag[3]);
+}
+
+FontFactory::FontFactory()
+    : fingerprint_(false) {
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/font_factory.h b/sfntly/cpp/src/sfntly/font_factory.h
new file mode 100644
index 0000000..63deff4
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/font_factory.h
@@ -0,0 +1,140 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_FONT_FACTORY_H_
+#define SFNTLY_CPP_SRC_SFNTLY_FONT_FACTORY_H_
+
+#include <vector>
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/port/type.h"
+#include "sfntly/font.h"
+
+namespace sfntly {
+
+class FontFactory : public RefCounted<FontFactory> {
+ public:
+  virtual ~FontFactory();
+
+  // Factory method for the construction of a font factory.
+  static CALLER_ATTACH FontFactory* GetInstance();
+
+  // Toggle whether fonts that are loaded are fingerprinted with a SHA-1 hash.
+  // If a font is fingerprinted then a SHA-1 hash is generated at load time and
+  // stored in the font. This is useful for uniquely identifying fonts. By
+  // default this is turned on.
+  // @param fingerprint whether fingerprinting should be turned on or off
+  // TODO(arthurhsu): IMPLEMENT: C++ port currently don't do any SHA-1
+  void FingerprintFont(bool fingerprint);
+  bool FingerprintFont();
+
+  // Load the font(s) from the input stream. The current settings on the factory
+  // are used during the loading process. One or more fonts are returned if the
+  // stream contains valid font data. Some font container formats may have more
+  // than one font and in this case multiple font objects will be returned. If
+  // the data in the stream cannot be parsed or is invalid an array of size zero
+  // will be returned.
+  void LoadFonts(InputStream* is, FontArray* output);
+
+  // ByteArray font loading
+  // Load the font(s) from the byte array. The current settings on the factory
+  // are used during the loading process. One or more fonts are returned if the
+  // stream contains valid font data. Some font container formats may have more
+  // than one font and in this case multiple font objects will be returned. If
+  // the data in the stream cannot be parsed or is invalid an array of size zero
+  // will be returned.
+  void LoadFonts(ByteVector* b, FontArray* output);
+
+  // Load the font(s) from the input stream into font builders. The current
+  // settings on the factory are used during the loading process. One or more
+  // font builders are returned if the stream contains valid font data. Some
+  // font container formats may have more than one font and in this case
+  // multiple font builder objects will be returned. If the data in the stream
+  // cannot be parsed or is invalid an array of size zero will be returned.
+  void LoadFontsForBuilding(InputStream* is, FontBuilderArray* output);
+
+  // Load the font(s) from the byte array into font builders. The current
+  // settings on the factory are used during the loading process. One or more
+  // font builders are returned if the stream contains valid font data. Some
+  // font container formats may have more than one font and in this case
+  // multiple font builder objects will be returned. If the data in the stream
+  // cannot be parsed or is invalid an array of size zero will be returned.
+  void LoadFontsForBuilding(ByteVector* b, FontBuilderArray* output);
+
+  // Font serialization
+  // Serialize the font to the output stream.
+  // NOTE: in this port we attempted not to implement I/O stream because dealing
+  //       with cross-platform I/O stream itself is big enough as a project.
+  //       Byte buffer it is.
+  void SerializeFont(Font* font, OutputStream* os);
+
+  // Set the table ordering to be used in serializing a font. The table ordering
+  // is an ordered list of table ids and tables will be serialized in the order
+  // given. Any tables whose id is not listed in the ordering will be placed in
+  // an unspecified order following those listed.
+  void SetSerializationTableOrdering(const IntegerList& table_ordering);
+
+  // Get an empty font builder for creating a new font from scratch.
+  CALLER_ATTACH Font::Builder* NewFontBuilder();
+
+ private:
+  // Offsets to specific elements in the underlying data. These offsets are
+  // relative to the start of the table or the start of sub-blocks within the
+  // table.
+  struct Offset {
+    enum {
+      // Offsets within the main directory.
+      kTTCTag = 0,
+      kVersion = 4,
+      kNumFonts = 8,
+      kOffsetTable = 12,
+
+      // TTC Version 2.0 extensions.
+      // Offsets from end of OffsetTable.
+      kulDsigTag = 0,
+      kulDsigLength = 4,
+      kulDsigOffset = 8
+    };
+  };
+
+  FontFactory();
+
+  CALLER_ATTACH Font* LoadSingleOTF(InputStream* is);
+  CALLER_ATTACH Font* LoadSingleOTF(WritableFontData* wfd);
+
+  void LoadCollection(InputStream* is, FontArray* output);
+  void LoadCollection(WritableFontData* wfd, FontArray* output);
+
+  CALLER_ATTACH Font::Builder* LoadSingleOTFForBuilding(InputStream* is);
+  CALLER_ATTACH Font::Builder*
+      LoadSingleOTFForBuilding(WritableFontData* wfd,
+                               int32_t offset_to_offset_table);
+
+  void LoadCollectionForBuilding(InputStream* is, FontBuilderArray* builders);
+  void LoadCollectionForBuilding(WritableFontData* ba,
+                                 FontBuilderArray* builders);
+
+  static bool IsCollection(PushbackInputStream* pbis);
+  static bool IsCollection(ReadableFontData* wfd);
+
+  bool fingerprint_;
+  IntegerList table_ordering_;
+};
+typedef Ptr<FontFactory> FontFactoryPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_FONT_FACTORY_H_
diff --git a/sfntly/cpp/src/sfntly/math/fixed1616.h b/sfntly/cpp/src/sfntly/math/fixed1616.h
new file mode 100644
index 0000000..4abbe18
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/math/fixed1616.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_MATH_FIXED1616_H_
+#define SFNTLY_CPP_SRC_SFNTLY_MATH_FIXED1616_H_
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+class Fixed1616 {
+ public:
+  static inline int32_t Integral(int32_t fixed) {
+    return (fixed >> 16);
+  }
+
+  static inline int32_t Fractional(int32_t fixed) {
+    return (fixed & 0xffff);
+  }
+
+  static inline int32_t Fixed(int32_t integral, int32_t fractional) {
+    return ((integral & 0xffff) << 16) | (fractional & 0xffff);
+  }
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_MATH_FIXED1616_H_
diff --git a/sfntly/cpp/src/sfntly/math/font_math.h b/sfntly/cpp/src/sfntly/math/font_math.h
new file mode 100644
index 0000000..f1cd2d2
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/math/font_math.h
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_MATH_FONT_MATH_H_
+#define SFNTLY_CPP_SRC_SFNTLY_MATH_FONT_MATH_H_
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+class FontMath {
+ public:
+  static int32_t Log2(int32_t a) {
+    int r = 0;  // r will be lg(a)
+    while (a != 0) {
+      a >>= 1;
+      r++;
+    }
+    return r - 1;
+  }
+
+  // Calculates the amount of padding needed. The values provided need to be in
+  // the same units. So, if the size is given as the number of bytes then the
+  // alignment size must also be specified as byte size to align to.
+  // @param size the size of the data that may need padding
+  // @param alignmentSize the number of units to align to
+  // @return the number of units needing to be added for alignment
+  static int32_t PaddingRequired(int32_t size, int32_t alignment_size) {
+    int32_t padding = alignment_size - (size % alignment_size);
+    return padding == alignment_size ? 0 : padding;
+  }
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_MATH_FONT_MATH_H_
diff --git a/sfntly/cpp/src/sfntly/port/atomic.h b/sfntly/cpp/src/sfntly/port/atomic.h
new file mode 100644
index 0000000..b381a52
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/atomic.h
@@ -0,0 +1,71 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_ATOMIC_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_ATOMIC_H_
+
+#if defined (WIN32)
+
+#include <windows.h>
+
+static inline size_t AtomicIncrement(size_t* address) {
+#if defined (_WIN64)
+  return InterlockedIncrement64(reinterpret_cast<LONGLONG*>(address));
+#else
+  return InterlockedIncrement(reinterpret_cast<LONG*>(address));
+#endif
+}
+
+static inline size_t AtomicDecrement(size_t* address) {
+#if defined (_WIN64)
+  return InterlockedDecrement64(reinterpret_cast<LONGLONG*>(address));
+#else
+  return InterlockedDecrement(reinterpret_cast<LONG*>(address));
+#endif
+}
+
+#elif defined (__APPLE__)
+
+#include <libkern/OSAtomic.h>
+
+static inline size_t AtomicIncrement(size_t* address) {
+  return OSAtomicIncrement32Barrier(reinterpret_cast<int32_t*>(address));
+}
+
+static inline size_t AtomicDecrement(size_t* address) {
+  return OSAtomicDecrement32Barrier(reinterpret_cast<int32_t*>(address));
+}
+
+// Originally we check __GCC_HAVE_SYNC_COMPARE_AND_SWAP_4, however, there are
+// issues that clang not carring over this definition.  Therefore we boldly
+// assume it's gcc or gcc-compatible here.  Compilation shall still fail since
+// the intrinsics used are GCC-specific.
+
+#else
+
+#include <stddef.h>
+
+static inline size_t AtomicIncrement(size_t* address) {
+  return __sync_add_and_fetch(address, 1);
+}
+
+static inline size_t AtomicDecrement(size_t* address) {
+  return __sync_sub_and_fetch(address, 1);
+}
+
+#endif  // WIN32
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_ATOMIC_H_
diff --git a/sfntly/cpp/src/sfntly/port/config.h b/sfntly/cpp/src/sfntly/port/config.h
new file mode 100644
index 0000000..0fcdffe
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/config.h
@@ -0,0 +1,28 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_CONFIG_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_CONFIG_H_
+
+#if !defined(SFNTLY_BIG_ENDIAN) && !defined(SFNTLY_LITTLE_ENDIAN)
+  #if defined (__ppc__) || defined (__ppc64__)
+    #define SFNTLY_BIG_ENDIAN
+  #else
+    #define SFNTLY_LITTLE_ENDIAN
+  #endif
+#endif
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_CONFIG_H_
diff --git a/sfntly/cpp/src/sfntly/port/endian.h b/sfntly/cpp/src/sfntly/port/endian.h
new file mode 100644
index 0000000..db58f0a
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/endian.h
@@ -0,0 +1,77 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_ENDIAN_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_ENDIAN_H_
+
+#include "sfntly/port/config.h"
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+static inline uint16_t EndianSwap16(uint16_t value) {
+  return (uint16_t)((value >> 8) | (value << 8));
+}
+
+static inline int32_t EndianSwap32(int32_t value) {
+  return (((value & 0x000000ff) << 24) |
+          ((value & 0x0000ff00) <<  8) |
+          ((value & 0x00ff0000) >>  8) |
+          ((value & 0xff000000) >> 24));
+}
+
+static inline uint64_t EndianSwap64(uint64_t value) {
+  return (((value & 0x00000000000000ffLL) << 56) |
+          ((value & 0x000000000000ff00LL) << 40) |
+          ((value & 0x0000000000ff0000LL) << 24) |
+          ((value & 0x00000000ff000000LL) << 8)  |
+          ((value & 0x000000ff00000000LL) >> 8)  |
+          ((value & 0x0000ff0000000000LL) >> 24) |
+          ((value & 0x00ff000000000000LL) >> 40) |
+          ((value & 0xff00000000000000LL) >> 56));
+}
+
+#ifdef SFNTLY_LITTLE_ENDIAN
+  #define ToBE16(n) EndianSwap16(n)
+  #define ToBE32(n) EndianSwap32(n)
+  #define ToBE64(n) EndianSwap64(n)
+  #define ToLE16(n) (n)
+  #define ToLE32(n) (n)
+  #define ToLE64(n) (n)
+  #define FromBE16(n) EndianSwap16(n)
+  #define FromBE32(n) EndianSwap32(n)
+  #define FromBE64(n) EndianSwap64(n)
+  #define FromLE16(n) (n)
+  #define FromLE32(n) (n)
+  #define FromLE64(n) (n)
+#else  // SFNTLY_BIG_ENDIAN
+  #define ToBE16(n) (n)
+  #define ToBE32(n) (n)
+  #define ToBE64(n) (n)
+  #define ToLE16(n) EndianSwap16(n)
+  #define ToLE32(n) EndianSwap32(n)
+  #define ToLE64(n) EndianSwap64(n)
+  #define FromBE16(n) (n)
+  #define FromBE32(n) (n)
+  #define FromBE64(n) (n)
+  #define FromLE16(n) EndianSwap16(n)
+  #define FromLE32(n) EndianSwap32(n)
+  #define FromLE64(n) EndianSwap64(n)
+#endif
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_ENDIAN_H_
diff --git a/sfntly/cpp/src/sfntly/port/exception_type.h b/sfntly/cpp/src/sfntly/port/exception_type.h
new file mode 100644
index 0000000..b96efcb
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/exception_type.h
@@ -0,0 +1,125 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// Exceptions used in sfntly
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_EXCEPTION_TYPE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_EXCEPTION_TYPE_H_
+
+#if !defined (SFNTLY_NO_EXCEPTION)
+
+#include <exception>
+#include <string>
+#include <sstream>
+
+namespace sfntly {
+
+class Exception : public std::exception {
+ public:
+  Exception() : what_("Unknown exception") {}
+  explicit Exception(const char* message) throw() { SetMessage(message); }
+  virtual ~Exception() throw() {}
+  virtual const char* what() const throw() { return what_.c_str(); }
+
+ protected:
+  void SetMessage(const char* message) throw() {
+    try {
+      what_ = message;
+    } catch (...) {}
+  }
+
+ private:
+  std::string what_;
+};
+
+class IndexOutOfBoundException : public Exception {
+ public:
+  IndexOutOfBoundException() throw() : Exception("Index out of bound") {}
+  explicit IndexOutOfBoundException(const char* message) throw()
+      : Exception(message) {}
+  IndexOutOfBoundException(const char* message, int32_t index) throw() {
+    try {
+      std::ostringstream msg;
+      msg << message;
+      msg << ":";
+      msg << index;
+      SetMessage(msg.str().c_str());
+    } catch (...) {}
+  }
+  virtual ~IndexOutOfBoundException() throw() {}
+};
+
+class IOException : public Exception {
+ public:
+  IOException() throw() : Exception("I/O exception") {}
+  explicit IOException(const char* message) throw() : Exception(message) {}
+  virtual ~IOException() throw() {}
+};
+
+class ArithmeticException : public Exception {
+ public:
+  ArithmeticException() throw() : Exception("Arithmetic exception") {}
+  explicit ArithmeticException(const char* message) throw()
+      : Exception(message) {}
+  virtual ~ArithmeticException() throw() {}
+};
+
+class UnsupportedOperationException : public Exception {
+ public:
+  UnsupportedOperationException() throw() :
+      Exception("Operation not supported") {}
+  explicit UnsupportedOperationException(const char* message) throw()
+      : Exception(message) {}
+  virtual ~UnsupportedOperationException() throw() {}
+};
+
+class RuntimeException : public Exception {
+ public:
+  RuntimeException() throw() : Exception("Runtime exception") {}
+  explicit RuntimeException(const char* message) throw()
+      : Exception(message) {}
+  virtual ~RuntimeException() throw() {}
+};
+
+class NoSuchElementException : public Exception {
+ public:
+  NoSuchElementException() throw() : Exception("No such element") {}
+  explicit NoSuchElementException(const char* message) throw()
+      : Exception(message) {}
+  virtual ~NoSuchElementException() throw() {}
+};
+
+class IllegalArgumentException : public Exception {
+ public:
+  IllegalArgumentException() throw() : Exception("Illegal argument") {}
+  explicit IllegalArgumentException(const char* message) throw()
+      : Exception(message) {}
+  virtual ~IllegalArgumentException() throw() {}
+};
+
+class IllegalStateException : public Exception {
+ public:
+  IllegalStateException() throw() : Exception("Illegal state") {}
+  explicit IllegalStateException(const char* message) throw()
+      : Exception(message) {}
+  virtual ~IllegalStateException() throw() {}
+};
+
+}  // namespace sfntly
+
+#endif  // #if !defined (SFNTLY_NO_EXCEPTION)
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_EXCEPTION_TYPE_H_
diff --git a/sfntly/cpp/src/sfntly/port/file_input_stream.cc b/sfntly/cpp/src/sfntly/port/file_input_stream.cc
new file mode 100644
index 0000000..5bcb434
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/file_input_stream.cc
@@ -0,0 +1,169 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#if defined (WIN32)
+#include <windows.h>
+#endif
+
+#include "sfntly/port/file_input_stream.h"
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+
+FileInputStream::FileInputStream()
+    : file_(NULL),
+      position_(0),
+      length_(0) {
+}
+
+FileInputStream::~FileInputStream() {
+  Close();
+}
+
+int32_t FileInputStream::Available() {
+  return length_ - position_;
+}
+
+void FileInputStream::Close() {
+  if (file_) {
+    fclose(file_);
+    length_ = 0;
+    position_ = 0;
+    file_ = NULL;
+  }
+}
+
+void FileInputStream::Mark(int32_t readlimit) {
+  // NOP
+  UNREFERENCED_PARAMETER(readlimit);
+}
+
+bool FileInputStream::MarkSupported() {
+  return false;
+}
+
+int32_t FileInputStream::Read() {
+  if (!file_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no opened file");
+#endif
+    return 0;
+  }
+  if (feof(file_)) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("eof reached");
+#endif
+    return 0;
+  }
+  byte_t value;
+  size_t length = fread(&value, 1, 1, file_);
+  position_ += length;
+  return value;
+}
+
+int32_t FileInputStream::Read(ByteVector* b) {
+  return Read(b, 0, b->size());
+}
+
+int32_t FileInputStream::Read(ByteVector* b, int32_t offset, int32_t length) {
+  assert(b);
+  if (!file_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no opened file");
+#endif
+    return 0;
+  }
+  if (feof(file_)) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("eof reached");
+#endif
+    return 0;
+  }
+  size_t read_count = std::min<size_t>(length_ - position_, length);
+  if (b->size() < (size_t)(offset + read_count)) {
+    b->resize((size_t)(offset + read_count));
+  }
+  int32_t actual_read = fread(&((*b)[offset]), 1, read_count, file_);
+  position_ += actual_read;
+  return actual_read;
+}
+
+void FileInputStream::Reset() {
+  // NOP
+}
+
+int64_t FileInputStream::Skip(int64_t n) {
+  if (!file_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no opened file");
+#endif
+    return 0;
+  }
+  int64_t skip_count = 0;
+  if (n < 0) {  // move backwards
+    skip_count = std::max<int64_t>(0 - (int64_t)position_, n);
+    position_ -= (size_t)(0 - skip_count);
+    fseek(file_, position_, SEEK_SET);
+  } else {
+    skip_count = std::min<size_t>(length_ - position_, (size_t)n);
+    position_ += (size_t)skip_count;
+    fseek(file_, (size_t)skip_count, SEEK_CUR);
+  }
+  return skip_count;
+}
+
+void FileInputStream::Unread(ByteVector* b) {
+  Unread(b, 0, b->size());
+}
+
+void FileInputStream::Unread(ByteVector* b, int32_t offset, int32_t length) {
+  assert(b);
+  assert(b->size() >= size_t(offset + length));
+  if (!file_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no opened file");
+#endif
+    return;
+  }
+  size_t unread_count = std::min<size_t>(position_, length);
+  fseek(file_, position_ - unread_count, SEEK_SET);
+  position_ -= unread_count;
+  Read(b, offset, length);
+  fseek(file_, position_ - unread_count, SEEK_SET);
+  position_ -= unread_count;
+}
+
+bool FileInputStream::Open(const char* file_path) {
+  assert(file_path);
+  if (file_) {
+    Close();
+  }
+#if defined (WIN32)
+  fopen_s(&file_, file_path, "rb");
+#else
+  file_ = fopen(file_path, "rb");
+#endif
+  if (file_ == NULL) {
+    return false;
+  }
+
+  fseek(file_, 0, SEEK_END);
+  length_ = ftell(file_);
+  fseek(file_, 0, SEEK_SET);
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/port/file_input_stream.h b/sfntly/cpp/src/sfntly/port/file_input_stream.h
new file mode 100644
index 0000000..cbca25f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/file_input_stream.h
@@ -0,0 +1,57 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_FILE_INPUT_STREAM_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_FILE_INPUT_STREAM_H_
+
+#include <stdio.h>
+
+#include "sfntly/port/input_stream.h"
+
+namespace sfntly {
+
+class FileInputStream : public PushbackInputStream {
+ public:
+  FileInputStream();
+  virtual ~FileInputStream();
+
+  // InputStream methods
+  virtual int32_t Available();
+  virtual void Close();
+  virtual void Mark(int32_t readlimit);
+  virtual bool MarkSupported();
+  virtual int32_t Read();
+  virtual int32_t Read(ByteVector* b);
+  virtual int32_t Read(ByteVector* b, int32_t offset, int32_t length);
+  virtual void Reset();
+  virtual int64_t Skip(int64_t n);
+
+  // PushbackInputStream methods
+  virtual void Unread(ByteVector* b);
+  virtual void Unread(ByteVector* b, int32_t offset, int32_t length);
+
+  // Own methods
+  virtual bool Open(const char* file_path);
+
+ private:
+  FILE* file_;
+  size_t position_;
+  size_t length_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_FILE_INPUT_STREAM_H_
diff --git a/sfntly/cpp/src/sfntly/port/input_stream.h b/sfntly/cpp/src/sfntly/port/input_stream.h
new file mode 100644
index 0000000..5d24036
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/input_stream.h
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_INPUT_STREAM_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_INPUT_STREAM_H_
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+// C++ equivalent to Java's OutputStream class
+class InputStream {
+ public:
+  // Make gcc -Wnon-virtual-dtor happy.
+  virtual ~InputStream() {}
+
+  virtual int32_t Available() = 0;
+  virtual void Close() = 0;
+  virtual void Mark(int32_t readlimit) = 0;
+  virtual bool MarkSupported() = 0;
+  virtual int32_t Read() = 0;
+  virtual int32_t Read(ByteVector* b) = 0;
+  virtual int32_t Read(ByteVector* b, int32_t offset, int32_t length) = 0;
+  virtual void Reset() = 0;
+  virtual int64_t Skip(int64_t n) = 0;
+};
+
+class PushbackInputStream : public InputStream {
+ public:
+  virtual void Unread(ByteVector* b) = 0;
+  virtual void Unread(ByteVector* b, int32_t offset, int32_t length) = 0;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_INPUT_STREAM_H_
diff --git a/sfntly/cpp/src/sfntly/port/java_iterator.h b/sfntly/cpp/src/sfntly/port/java_iterator.h
new file mode 100644
index 0000000..0a99bca
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/java_iterator.h
@@ -0,0 +1,94 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_JAVA_ITERATOR_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_JAVA_ITERATOR_H_
+
+#include "sfntly/port/refcount.h"
+
+// Interface of Java iterator.
+// This is a forward read-only iterator that represents java.util.Iterator<E>
+
+namespace sfntly {
+
+template <typename ReturnType, typename ContainerBase>
+class Iterator : public virtual RefCount {
+ public:
+  virtual ~Iterator() {}
+  virtual ContainerBase* container_base() = 0;
+
+ protected:
+  Iterator() {}
+  NO_COPY_AND_ASSIGN(Iterator);
+};
+
+template <typename ReturnType, typename Container,
+          typename ContainerBase = Container>
+class PODIterator : public Iterator<ReturnType, ContainerBase>,
+                    public RefCounted< PODIterator<ReturnType, Container> > {
+ public:
+  explicit PODIterator(Container* container) : container_(container) {}
+  virtual ~PODIterator() {}
+  virtual ContainerBase* container_base() {
+    return static_cast<ContainerBase*>(container_);
+  }
+
+  virtual bool HasNext() = 0;
+  virtual ReturnType Next() = 0;
+  virtual void Remove() {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    // Default to no support.
+    throw UnsupportedOperationException();
+#endif
+  }
+
+ protected:
+  Container* container() { return container_; }
+
+ private:
+  Container* container_;  // Dumb pointer is used to avoid circular ref-counting
+};
+
+template <typename ReturnType, typename Container,
+          typename ContainerBase = Container>
+class RefIterator : public Iterator<ReturnType, ContainerBase>,
+                    public RefCounted< RefIterator<ReturnType, Container> > {
+ public:
+  explicit RefIterator(Container* container) : container_(container) {}
+  virtual ~RefIterator() {}
+  virtual ContainerBase* container_base() {
+    return static_cast<ContainerBase*>(container_);
+  }
+
+  virtual bool HasNext() = 0;
+  CALLER_ATTACH virtual ReturnType* Next() = 0;
+  virtual void Remove() {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    // Default to no support.
+    throw UnsupportedOperationException();
+#endif
+  }
+
+ protected:
+  Container* container() { return container_; }
+
+ private:
+  Container* container_;  // Dumb pointer is used to avoid circular ref-counting
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_JAVA_ITERATOR_H_
diff --git a/sfntly/cpp/src/sfntly/port/lock.cc b/sfntly/cpp/src/sfntly/port/lock.cc
new file mode 100644
index 0000000..6c0c309
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/lock.cc
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/port/lock.h"
+
+namespace sfntly {
+
+#if defined (WIN32)
+
+Lock::Lock() {
+  // The second parameter is the spin count, for short-held locks it avoid the
+  // contending thread from going to sleep which helps performance greatly.
+  ::InitializeCriticalSectionAndSpinCount(&os_lock_, 2000);
+}
+
+Lock::~Lock() {
+  ::DeleteCriticalSection(&os_lock_);
+}
+
+bool Lock::Try() {
+  if (::TryEnterCriticalSection(&os_lock_) != FALSE) {
+    return true;
+  }
+  return false;
+}
+
+void Lock::Acquire() {
+  ::EnterCriticalSection(&os_lock_);
+}
+
+void Lock::Unlock() {
+  ::LeaveCriticalSection(&os_lock_);
+}
+
+#else  // We assume it's pthread
+
+Lock::Lock() {
+  pthread_mutex_init(&os_lock_, NULL);
+}
+
+Lock::~Lock() {
+  pthread_mutex_destroy(&os_lock_);
+}
+
+bool Lock::Try() {
+  return (pthread_mutex_trylock(&os_lock_) == 0);
+}
+
+void Lock::Acquire() {
+  pthread_mutex_lock(&os_lock_);
+}
+
+void Lock::Unlock() {
+  pthread_mutex_unlock(&os_lock_);
+}
+
+#endif
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/port/lock.h b/sfntly/cpp/src/sfntly/port/lock.h
new file mode 100644
index 0000000..b2e29bf
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/lock.h
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_LOCK_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_LOCK_H_
+
+#if defined (WIN32)
+#include <windows.h>
+#else  // Assume pthread.
+#include <pthread.h>
+#include <errno.h>
+#endif
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+#if defined (WIN32)
+  typedef CRITICAL_SECTION OSLockType;
+#else  // Assume pthread.
+  typedef pthread_mutex_t OSLockType;
+#endif
+
+class Lock {
+ public:
+  Lock();
+  ~Lock();
+
+  // If the lock is not held, take it and return true.  If the lock is already
+  // held by something else, immediately return false.
+  bool Try();
+
+  // Take the lock, blocking until it is available if necessary.
+  void Acquire();
+
+  // Release the lock.  This must only be called by the lock's holder: after
+  // a successful call to Try, or a call to Lock.
+  void Unlock();
+
+ private:
+  OSLockType os_lock_;
+  NO_COPY_AND_ASSIGN(Lock);
+};
+
+// A helper class that acquires the given Lock while the AutoLock is in scope.
+class AutoLock {
+ public:
+  explicit AutoLock(Lock& lock) : lock_(lock) {
+    lock_.Acquire();
+  }
+
+  ~AutoLock() {
+    lock_.Unlock();
+  }
+
+ private:
+  Lock& lock_;
+  NO_COPY_AND_ASSIGN(AutoLock);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_LOCK_H_
diff --git a/sfntly/cpp/src/sfntly/port/memory_input_stream.cc b/sfntly/cpp/src/sfntly/port/memory_input_stream.cc
new file mode 100755
index 0000000..56ee81e
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/memory_input_stream.cc
@@ -0,0 +1,147 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#if defined (WIN32)
+#include <windows.h>
+#endif
+
+#include <string.h>
+
+#include "sfntly/port/memory_input_stream.h"
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+
+MemoryInputStream::MemoryInputStream()
+    : buffer_(NULL),
+      position_(0),
+      length_(0) {
+}
+
+MemoryInputStream::~MemoryInputStream() {
+  Close();
+}
+
+int32_t MemoryInputStream::Available() {
+  return length_ - position_;
+}
+
+void MemoryInputStream::Close() {
+}
+
+void MemoryInputStream::Mark(int32_t readlimit) {
+  // NOP
+  UNREFERENCED_PARAMETER(readlimit);
+}
+
+bool MemoryInputStream::MarkSupported() {
+  return false;
+}
+
+int32_t MemoryInputStream::Read() {
+  if (!buffer_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no memory attached");
+#endif
+    return 0;
+  }
+  if (position_ >= length_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("eof reached");
+#endif
+    return 0;
+  }
+  byte_t value = buffer_[position_++];
+  return value;
+}
+
+int32_t MemoryInputStream::Read(ByteVector* b) {
+  return Read(b, 0, b->size());
+}
+
+int32_t MemoryInputStream::Read(ByteVector* b, int32_t offset, int32_t length) {
+  assert(b);
+  if (!buffer_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no memory attached");
+#endif
+    return 0;
+  }
+  if (position_ >= length_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("eof reached");
+#endif
+    return 0;
+  }
+  size_t read_count = std::min<size_t>(length_ - position_, length);
+  if (b->size() < (size_t)(offset + read_count)) {
+    b->resize((size_t)(offset + read_count));
+  }
+  memcpy(&((*b)[offset]), buffer_ + position_, read_count);
+  position_ += read_count;
+  return read_count;
+}
+
+void MemoryInputStream::Reset() {
+  // NOP
+}
+
+int64_t MemoryInputStream::Skip(int64_t n) {
+  if (!buffer_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no memory attached");
+#endif
+    return 0;
+  }
+  int64_t skip_count = 0;
+  if (n < 0) {  // move backwards
+    skip_count = std::max<int64_t>(0 - (int64_t)position_, n);
+    position_ -= (size_t)(0 - skip_count);
+  } else {
+    skip_count = std::min<size_t>(length_ - position_, (size_t)n);
+    position_ += (size_t)skip_count;
+  }
+  return skip_count;
+}
+
+void MemoryInputStream::Unread(ByteVector* b) {
+  Unread(b, 0, b->size());
+}
+
+void MemoryInputStream::Unread(ByteVector* b, int32_t offset, int32_t length) {
+  assert(b);
+  assert(b->size() >= size_t(offset + length));
+  if (!buffer_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("no memory attached");
+#endif
+    return;
+  }
+  size_t unread_count = std::min<size_t>(position_, length);
+  position_ -= unread_count;
+  Read(b, offset, length);
+  position_ -= unread_count;
+}
+
+bool MemoryInputStream::Attach(const byte_t* buffer, size_t length) {
+  assert(buffer);
+  assert(length);
+  buffer_ = buffer;
+  length_ = length;
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/port/memory_input_stream.h b/sfntly/cpp/src/sfntly/port/memory_input_stream.h
new file mode 100755
index 0000000..bc861c3
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/memory_input_stream.h
@@ -0,0 +1,57 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_MEMORY_INPUT_STREAM_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_MEMORY_INPUT_STREAM_H_
+
+#include <stdio.h>
+
+#include "sfntly/port/input_stream.h"
+
+namespace sfntly {
+
+class MemoryInputStream : public PushbackInputStream {
+ public:
+  MemoryInputStream();
+  virtual ~MemoryInputStream();
+
+  // InputStream methods
+  virtual int32_t Available();
+  virtual void Close();
+  virtual void Mark(int32_t readlimit);
+  virtual bool MarkSupported();
+  virtual int32_t Read();
+  virtual int32_t Read(ByteVector* b);
+  virtual int32_t Read(ByteVector* b, int32_t offset, int32_t length);
+  virtual void Reset();
+  virtual int64_t Skip(int64_t n);
+
+  // PushbackInputStream methods
+  virtual void Unread(ByteVector* b);
+  virtual void Unread(ByteVector* b, int32_t offset, int32_t length);
+
+  // Own methods
+  virtual bool Attach(const byte_t* buffer, size_t length);
+
+ private:
+  const byte_t* buffer_;
+  size_t position_;
+  size_t length_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_MEMORY_INPUT_STREAM_H_
diff --git a/sfntly/cpp/src/sfntly/port/memory_output_stream.cc b/sfntly/cpp/src/sfntly/port/memory_output_stream.cc
new file mode 100644
index 0000000..f2ff2e3
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/memory_output_stream.cc
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/port/memory_output_stream.h"
+
+namespace sfntly {
+
+MemoryOutputStream::MemoryOutputStream() {
+}
+
+MemoryOutputStream::~MemoryOutputStream() {
+}
+
+void MemoryOutputStream::Write(ByteVector* buffer) {
+  store_.insert(store_.end(), buffer->begin(), buffer->end());
+}
+
+void MemoryOutputStream::Write(ByteVector* buffer,
+                               int32_t offset,
+                               int32_t length) {
+  assert(buffer);
+  if (offset >= 0 && length > 0) {
+    store_.insert(store_.end(),
+                  buffer->begin() + offset,
+                  buffer->begin() + offset + length);
+  } else {
+#if !defined(SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#endif
+  }
+}
+
+void MemoryOutputStream::Write(byte_t* buffer, int32_t offset, int32_t length) {
+  assert(buffer);
+  if (offset >= 0 && length > 0) {
+    store_.insert(store_.end(), buffer + offset, buffer + offset + length);
+  } else {
+#if !defined(SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#endif
+  }
+}
+
+void MemoryOutputStream::Write(byte_t b) {
+  store_.push_back(b);
+}
+
+byte_t* MemoryOutputStream::Get() {
+  if (store_.empty()) {
+    return NULL;
+  }
+  return &(store_[0]);
+}
+
+size_t MemoryOutputStream::Size() {
+  return store_.size();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/port/memory_output_stream.h b/sfntly/cpp/src/sfntly/port/memory_output_stream.h
new file mode 100644
index 0000000..d1eda7f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/memory_output_stream.h
@@ -0,0 +1,51 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_MEMORY_OUTPUT_STREAM_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_MEMORY_OUTPUT_STREAM_H_
+
+#include <cstddef>
+#include <vector>
+
+#include "sfntly/port/type.h"
+#include "sfntly/port/output_stream.h"
+
+namespace sfntly {
+
+// OutputStream backed by STL vector
+
+class MemoryOutputStream : public OutputStream {
+ public:
+  MemoryOutputStream();
+  virtual ~MemoryOutputStream();
+
+  virtual void Close() {}  // no-op
+  virtual void Flush() {}  // no-op
+  virtual void Write(ByteVector* buffer);
+  virtual void Write(ByteVector* buffer, int32_t offset, int32_t length);
+  virtual void Write(byte_t* buffer, int32_t offset, int32_t length);
+  virtual void Write(byte_t b);
+
+  byte_t* Get();
+  size_t Size();
+
+ private:
+  std::vector<byte_t> store_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_MEMORY_OUTPUT_STREAM_H_
diff --git a/sfntly/cpp/src/sfntly/port/output_stream.h b/sfntly/cpp/src/sfntly/port/output_stream.h
new file mode 100644
index 0000000..64a6024
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/output_stream.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_OUTPUT_STREAM_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_OUTPUT_STREAM_H_
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+// C++ equivalent to Java's OutputStream class
+class OutputStream {
+ public:
+  // Make gcc -Wnon-virtual-dtor happy.
+  virtual ~OutputStream() {}
+
+  virtual void Close() = 0;
+  virtual void Flush() = 0;
+  virtual void Write(ByteVector* buffer) = 0;
+  virtual void Write(byte_t b) = 0;
+
+  // Note: C++ port offered both versions of Write() here.  The first one is
+  //       better because it does check bounds.  The second one is there for
+  //       performance concerns.
+  virtual void Write(ByteVector* buffer, int32_t offset, int32_t length) = 0;
+
+  // Note: Caller is responsible for the boundary of buffer.
+  virtual void Write(byte_t* buffer, int32_t offset, int32_t length) = 0;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_OUTPUT_STREAM_H_
diff --git a/sfntly/cpp/src/sfntly/port/refcount.h b/sfntly/cpp/src/sfntly/port/refcount.h
new file mode 100644
index 0000000..eed5162
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/refcount.h
@@ -0,0 +1,277 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// Object reference count and smart pointer implementation.
+
+// Smart pointer usage in sfntly:
+//
+// sfntly carries a smart pointer implementation like COM.  Ref-countable object
+// type inherits from RefCounted<>, which have AddRef and Release just like
+// IUnknown (but no QueryInterface).  Use a Ptr<> based smart pointer to hold
+// the object so that the object ref count is handled correctly.
+//
+// class Foo : public RefCounted<Foo> {
+//  public:
+//   static Foo* CreateInstance() {
+//     Ptr<Foo> obj = new Foo();  // ref count = 1
+//     return obj.Detach();
+//   }
+// };
+// typedef Ptr<Foo> FooPtr;  // common short-hand notation
+// FooPtr obj;
+// obj.Attach(Foo::CreatedInstance());  // ref count = 1
+// {
+//   FooPtr obj2 = obj;  // ref count = 2
+// }  // ref count = 1, obj2 out of scope
+// obj.Release();  // ref count = 0, object destroyed
+
+// Notes on usage:
+// 1. Virtual inherit from RefCount interface in base class if smart pointers
+//    are going to be defined.
+// 2. All RefCounted objects must be instantiated on the heap.  Allocating the
+//    object on stack will cause crash.
+// 3. Be careful when you have complex inheritance.  For example,
+//    class A : public RefCounted<A>;
+//    class B : public A, public RefCounted<B>;
+//    In this case the smart pointer is pretty dumb and don't count on it to
+//    nicely destroy your objects as designed. Try refactor your code like
+//    class I;  // the common interface and implementations
+//    class A : public I, public RefCounted<A>;  // A specific implementation
+//    class B : public I, public RefCounted<B>;  // B specific implementation
+// 4. Smart pointers here are very bad candidates for function parameters.  Use
+//    dumb pointers in function parameter list.
+// 5. When down_cast is performed on a dangling pointer due to bugs in code,
+//    VC++ will generate SEH which is not handled well in VC++ debugger.  One
+//    can use WinDBG to run it and get the faulting stack.
+// 6. Idioms for heap object as return value
+//    Foo* createFoo() { FooPtr obj = new Foo(); return obj.Detach(); }
+//    Foo* passthru() { FooPtr obj = createFoo(), return obj; }
+//    FooPtr end_scope_pointer;
+//    end_scope_pointer.Attach(passThrough);
+//    If you are not passing that object back, you are the end of scope.
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_REFCOUNT_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_REFCOUNT_H_
+
+#if !defined (NDEBUG)
+  #define ENABLE_OBJECT_COUNTER
+//  #define REF_COUNT_DEBUGGING
+#endif
+
+#if defined (REF_COUNT_DEBUGGING)
+  #include <stdio.h>
+  #include <typeinfo>
+#endif
+
+#include "sfntly/port/atomic.h"
+#include "sfntly/port/type.h"
+
+// Special tag for functions that requires caller to attach instead of using
+// assignment operators.
+#define CALLER_ATTACH
+
+#if defined (REF_COUNT_DEBUGGING)
+  #define DEBUG_OUTPUT(a) \
+      fprintf(stderr, "%s%s:oc=%d,oid=%d,rc=%d\n", a, \
+              typeid(this).name(), object_counter_, object_id_, ref_count_)
+#else
+  #define DEBUG_OUTPUT(a)
+#endif
+
+#if defined (_MSC_VER)
+  // VC 2008/2010 incorrectly gives this warning for pure virtual functions
+  // in virtual inheritance.  The only way to get around it is to disable it.
+  #pragma warning(disable:4250)
+#endif
+
+namespace sfntly {
+
+class RefCount {
+ public:
+  // Make gcc -Wnon-virtual-dtor happy.
+  virtual ~RefCount() {}
+
+  virtual size_t AddRef() const = 0;
+  virtual size_t Release() const = 0;
+};
+
+template <typename T>
+class NoAddRefRelease : public T {
+ public:
+  NoAddRefRelease();
+  ~NoAddRefRelease();
+
+ private:
+  virtual size_t AddRef() const = 0;
+  virtual size_t Release() const = 0;
+};
+
+template <typename TDerived>
+class RefCounted : virtual public RefCount {
+ public:
+  RefCounted() : ref_count_(0) {
+#if defined (ENABLE_OBJECT_COUNTER)
+    object_id_ = AtomicIncrement(&next_id_);
+    AtomicIncrement(&object_counter_);
+    DEBUG_OUTPUT("C ");
+#endif
+  }
+  RefCounted(const RefCounted<TDerived>&) : ref_count_(0) {}
+  virtual ~RefCounted() {
+#if defined (ENABLE_OBJECT_COUNTER)
+    AtomicDecrement(&object_counter_);
+    DEBUG_OUTPUT("D ");
+#endif
+  }
+
+  RefCounted<TDerived>& operator=(const RefCounted<TDerived>&) {
+    // Each object maintains own ref count, don't propagate.
+    return *this;
+  }
+
+  virtual size_t AddRef() const {
+    size_t new_count = AtomicIncrement(&ref_count_);
+    DEBUG_OUTPUT("A ");
+    return new_count;
+  }
+
+  virtual size_t Release() const {
+    size_t new_ref_count = AtomicDecrement(&ref_count_);
+    DEBUG_OUTPUT("R ");
+    if (new_ref_count == 0) {
+      // A C-style is used to cast away const-ness and to derived.
+      // lint does not like this but this is how it works.
+      delete (TDerived*)(this);
+    }
+    return new_ref_count;
+  }
+
+  mutable size_t ref_count_;  // reference count of current object
+#if defined (ENABLE_OBJECT_COUNTER)
+  static size_t object_counter_;
+  static size_t next_id_;
+  mutable size_t object_id_;
+#endif
+};
+
+#if defined (ENABLE_OBJECT_COUNTER)
+template <typename TDerived> size_t RefCounted<TDerived>::object_counter_ = 0;
+template <typename TDerived> size_t RefCounted<TDerived>::next_id_ = 0;
+#endif
+
+// semi-smart pointer for RefCount derived objects, similar to CComPtr
+template <typename T>
+class Ptr {
+ public:
+  Ptr() : p_(NULL) {
+  }
+
+  // This constructor shall not be explicit.
+  // lint does not like this but this is how it works.
+  Ptr(T* pT) : p_(NULL) {
+    *this = pT;
+  }
+
+  Ptr(const Ptr<T>& p) : p_(NULL) {
+    *this = p;
+  }
+
+  ~Ptr() {
+    Release();
+  }
+
+  T* operator=(T* pT) {
+    if (p_ == pT) {
+      return p_;
+    }
+    if (pT) {
+      RefCount* p = static_cast<RefCount*>(pT);
+      if (p == NULL) {
+        return NULL;
+      }
+      p->AddRef();  // always AddRef() before Release()
+    }
+    Release();
+    p_ = pT;
+    return p_;
+  }
+
+  T* operator=(const Ptr<T>& p) {
+    if (p_ == p.p_) {
+      return p_;
+    }
+    return operator=(p.p_);
+  }
+
+  operator T*&() {
+    return p_;
+  }
+
+  T& operator*() const {
+    return *p_;  // It can throw!
+  }
+
+  NoAddRefRelease<T>* operator->() const {
+    return (NoAddRefRelease<T>*)p_;  // It can throw!
+  }
+
+  bool operator!() const {
+    return (p_ == NULL);
+  }
+
+  bool operator<(const Ptr<T>& p) const {
+    return (p_ < p.p_);
+  }
+
+  bool operator!=(T* pT) const {
+    return !operator==(pT);
+  }
+
+  bool operator==(T* pT) const {
+    return (p_ == pT);
+  }
+
+  size_t Release() const {
+    size_t ref_count = 0;
+    if (p_) {
+      RefCount* p = static_cast<RefCount*>(p_);
+      if (p) {
+        ref_count = p->Release();
+      }
+      p_ = NULL;
+    }
+    return ref_count;
+  }
+
+  void Attach(T* pT) {
+    if (p_ != pT) {
+      Release();
+      p_ = pT;
+    }
+  }
+
+  T* Detach() {
+    T* pT = p_;
+    p_ = NULL;
+    return pT;
+  }
+
+  mutable T* p_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_REFCOUNT_H_
diff --git a/sfntly/cpp/src/sfntly/port/type.h b/sfntly/cpp/src/sfntly/port/type.h
new file mode 100644
index 0000000..20a5ba8
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/port/type.h
@@ -0,0 +1,102 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_PORT_TYPE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_PORT_TYPE_H_
+
+#include <assert.h>
+
+#if defined (_MSC_VER) && (_MSC_VER < 1600)
+  typedef unsigned char     uint8_t;
+  typedef signed char       int8_t;
+  typedef unsigned __int16  uint16_t;
+  typedef signed __int16    int16_t;
+  typedef unsigned __int32  uint32_t;
+  typedef signed __int32    int32_t;
+  typedef unsigned __int64  uint64_t;
+  typedef signed __int64    int64_t;
+  // Definitions to avoid ICU redefinition issue
+  #define U_HAVE_INT8_T 1
+  #define U_HAVE_UINT8_T 1
+  #define U_HAVE_INT16_T 1
+  #define U_HAVE_UINT16_T 1
+  #define U_HAVE_INT32_T 1
+  #define U_HAVE_UINT32_T 1
+  #define U_HAVE_INT64_T 1
+  #define U_HAVE_UINT64_T 1
+#else
+  #include <stdint.h>
+#endif
+
+#include <cstddef>
+#include <vector>
+#include <set>
+
+namespace sfntly {
+
+typedef uint8_t   byte_t;
+typedef uint16_t  word_t;
+typedef uint32_t  dword_t;
+typedef uint64_t  qword_t;
+
+typedef std::vector<byte_t> ByteVector;
+typedef std::vector<int32_t> IntegerList;
+typedef std::set<int32_t> IntegerSet;
+
+// A macro to disallow the copy constructor and operator= functions.
+// This should be used in the private: declarations for a class.
+#define NO_COPY_AND_ASSIGN(TypeName) \
+  TypeName(const TypeName&);               \
+  void operator=(const TypeName&)
+
+}  // namespace sfntly
+
+// Make google3 happy since it prohibits RTTI.
+template<typename To, typename From>
+inline To implicit_cast(From const &f) {
+  return f;
+}
+
+template<typename To, typename From>     // use like this: down_cast<T*>(foo);
+inline To down_cast(From* f) {                   // so we only accept pointers
+  // Ensures that To is a sub-type of From *.  This test is here only
+  // for compile-time type checking, and has no overhead in an
+  // optimized build at run-time, as it will be optimized away
+  // completely.
+#if defined (_MSC_VER)
+  #pragma warning(push)
+  #pragma warning(disable:4127)  // disable "conditional expression is constant"
+#endif
+  if (false) {
+    implicit_cast<From*, To>(0);
+  }
+#if defined (_MSC_VER)
+  #pragma warning(pop)
+#endif
+
+// The following code is the only place for RTTI.  It is done so to allow
+// additional type checking when SFNTLY_TYPE_VERIFICATION is defined.
+#if defined (SFNTLY_TYPE_VERIFICATION)
+  assert(f == NULL || dynamic_cast<To>(f) != NULL);
+#endif
+  return static_cast<To>(f);
+}
+
+#if !defined(WIN32)
+  #define UNREFERENCED_PARAMETER(p) do { (void)p; } while (0)
+#endif
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_PORT_TYPE_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/big_glyph_metrics.cc b/sfntly/cpp/src/sfntly/table/bitmap/big_glyph_metrics.cc
new file mode 100644
index 0000000..d853212
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/big_glyph_metrics.cc
@@ -0,0 +1,171 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/big_glyph_metrics.h"
+
+namespace sfntly {
+/******************************************************************************
+ * BigGlyphMetrics class
+ ******************************************************************************/
+BigGlyphMetrics::BigGlyphMetrics(ReadableFontData* data)
+    : GlyphMetrics(data) {
+}
+
+BigGlyphMetrics::~BigGlyphMetrics() {
+}
+
+int32_t BigGlyphMetrics::Height() {
+  return data_->ReadByte(Offset::kHeight);
+}
+
+int32_t BigGlyphMetrics::Width() {
+  return data_->ReadByte(Offset::kWidth);
+}
+
+int32_t BigGlyphMetrics::HoriBearingX() {
+  return data_->ReadByte(Offset::kHoriBearingX);
+}
+
+int32_t BigGlyphMetrics::HoriBearingY() {
+  return data_->ReadByte(Offset::kHoriBearingY);
+}
+
+int32_t BigGlyphMetrics::HoriAdvance() {
+  return data_->ReadByte(Offset::kHoriAdvance);
+}
+
+int32_t BigGlyphMetrics::VertBearingX() {
+  return data_->ReadByte(Offset::kVertBearingX);
+}
+
+int32_t BigGlyphMetrics::VertBearingY() {
+  return data_->ReadByte(Offset::kVertBearingY);
+}
+
+int32_t BigGlyphMetrics::VertAdvance() {
+  return data_->ReadByte(Offset::kVertAdvance);
+}
+
+/******************************************************************************
+ * BigGlyphMetrics::Builder class
+ ******************************************************************************/
+BigGlyphMetrics::Builder::Builder(WritableFontData* data)
+    : GlyphMetrics::Builder(data) {
+}
+
+BigGlyphMetrics::Builder::Builder(ReadableFontData* data)
+    : GlyphMetrics::Builder(data) {
+}
+
+BigGlyphMetrics::Builder::~Builder() {
+}
+
+int32_t BigGlyphMetrics::Builder::Height() {
+  return InternalReadData()->ReadByte(Offset::kHeight);
+}
+
+void BigGlyphMetrics::Builder::SetHeight(byte_t height) {
+  InternalWriteData()->WriteByte(Offset::kHeight, height);
+}
+
+int32_t BigGlyphMetrics::Builder::Width() {
+  return InternalReadData()->ReadByte(Offset::kWidth);
+}
+
+void BigGlyphMetrics::Builder::SetWidth(byte_t width) {
+  InternalWriteData()->WriteByte(Offset::kWidth, width);
+}
+
+int32_t BigGlyphMetrics::Builder::HoriBearingX() {
+  return InternalReadData()->ReadByte(Offset::kHoriBearingX);
+}
+
+void BigGlyphMetrics::Builder::SetHoriBearingX(byte_t bearing) {
+  InternalWriteData()->WriteByte(Offset::kHoriBearingX, bearing);
+}
+
+int32_t BigGlyphMetrics::Builder::HoriBearingY() {
+  return InternalReadData()->ReadByte(Offset::kHoriBearingY);
+}
+
+void BigGlyphMetrics::Builder::SetHoriBearingY(byte_t bearing) {
+  InternalWriteData()->WriteByte(Offset::kHoriBearingY, bearing);
+}
+
+int32_t BigGlyphMetrics::Builder::HoriAdvance() {
+  return InternalReadData()->ReadByte(Offset::kHoriAdvance);
+}
+
+void BigGlyphMetrics::Builder::SetHoriAdvance(byte_t advance) {
+  InternalWriteData()->WriteByte(Offset::kHoriAdvance, advance);
+}
+
+int32_t BigGlyphMetrics::Builder::VertBearingX() {
+  return InternalReadData()->ReadByte(Offset::kVertBearingX);
+}
+
+void BigGlyphMetrics::Builder::SetVertBearingX(byte_t bearing) {
+  InternalWriteData()->WriteByte(Offset::kVertBearingX, bearing);
+}
+
+int32_t BigGlyphMetrics::Builder::VertBearingY() {
+  return InternalReadData()->ReadByte(Offset::kVertBearingY);
+}
+
+void BigGlyphMetrics::Builder::SetVertBearingY(byte_t bearing) {
+  InternalWriteData()->WriteByte(Offset::kVertBearingY, bearing);
+}
+
+int32_t BigGlyphMetrics::Builder::VertAdvance() {
+  return InternalReadData()->ReadByte(Offset::kVertAdvance);
+}
+
+void BigGlyphMetrics::Builder::SetVertAdvance(byte_t advance) {
+  InternalWriteData()->WriteByte(Offset::kVertAdvance, advance);
+}
+
+CALLER_ATTACH FontDataTable*
+    BigGlyphMetrics::Builder::SubBuildTable(ReadableFontData* data) {
+  BigGlyphMetricsPtr output = new BigGlyphMetrics(data);
+  return output.Detach();
+}
+
+void BigGlyphMetrics::Builder::SubDataSet() {
+  // NOP.
+}
+
+int32_t BigGlyphMetrics::Builder::SubDataSizeToSerialize() {
+  return 0;
+}
+
+bool BigGlyphMetrics::Builder::SubReadyToSerialize() {
+  return false;
+}
+
+int32_t BigGlyphMetrics::Builder::SubSerialize(WritableFontData* new_data) {
+  return Data()->CopyTo(new_data);
+}
+
+// static
+CALLER_ATTACH
+BigGlyphMetrics::Builder* BigGlyphMetrics::Builder::CreateBuilder() {
+  WritableFontDataPtr data;
+  data.Attach(WritableFontData::CreateWritableFontData(Offset::kMetricsLength));
+  BigGlyphMetricsBuilderPtr output = new BigGlyphMetrics::Builder(data);
+  return output.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/big_glyph_metrics.h b/sfntly/cpp/src/sfntly/table/bitmap/big_glyph_metrics.h
new file mode 100644
index 0000000..a91601c
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/big_glyph_metrics.h
@@ -0,0 +1,96 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BIG_GLYPH_METRICS_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BIG_GLYPH_METRICS_H_
+
+#include "sfntly/table/bitmap/glyph_metrics.h"
+
+namespace sfntly {
+
+class BigGlyphMetrics : public GlyphMetrics,
+                        public RefCounted<BigGlyphMetrics> {
+ public:
+  struct Offset {
+    enum {
+      kMetricsLength = 8,
+
+      kHeight = 0,
+      kWidth = 1,
+      kHoriBearingX = 2,
+      kHoriBearingY = 3,
+      kHoriAdvance = 4,
+      kVertBearingX = 5,
+      kVertBearingY = 6,
+      kVertAdvance = 7,
+    };
+  };
+
+  class Builder : public GlyphMetrics::Builder,
+                  public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    explicit Builder(WritableFontData* data);
+    explicit Builder(ReadableFontData* data);
+
+    virtual ~Builder();
+
+    int32_t Height();
+    void SetHeight(byte_t height);
+    int32_t Width();
+    void SetWidth(byte_t width);
+    int32_t HoriBearingX();
+    void SetHoriBearingX(byte_t bearing);
+    int32_t HoriBearingY();
+    void SetHoriBearingY(byte_t bearing);
+    int32_t HoriAdvance();
+    void SetHoriAdvance(byte_t advance);
+    int32_t VertBearingX();
+    void SetVertBearingX(byte_t bearing);
+    int32_t VertBearingY();
+    void SetVertBearingY(byte_t bearing);
+    int32_t VertAdvance();
+    void SetVertAdvance(byte_t advance);
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    // Static instantiation function.
+    static CALLER_ATTACH Builder* CreateBuilder();
+  };
+
+  explicit BigGlyphMetrics(ReadableFontData* data);
+  virtual ~BigGlyphMetrics();
+
+  int32_t Height();
+  int32_t Width();
+  int32_t HoriBearingX();
+  int32_t HoriBearingY();
+  int32_t HoriAdvance();
+  int32_t VertBearingX();
+  int32_t VertBearingY();
+  int32_t VertAdvance();
+};
+typedef Ptr<BigGlyphMetrics> BigGlyphMetricsPtr;
+typedef Ptr<BigGlyphMetrics::Builder> BigGlyphMetricsBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BIG_GLYPH_METRICS_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph.cc b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph.cc
new file mode 100644
index 0000000..334a0c0
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph.cc
@@ -0,0 +1,101 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/bitmap_glyph.h"
+#include "sfntly/table/bitmap/simple_bitmap_glyph.h"
+#include "sfntly/table/bitmap/composite_bitmap_glyph.h"
+
+namespace sfntly {
+/******************************************************************************
+ * BitmapGlyph class
+ ******************************************************************************/
+BitmapGlyph::~BitmapGlyph() {
+}
+
+CALLER_ATTACH BitmapGlyph* BitmapGlyph::CreateGlyph(ReadableFontData* data,
+                                                    int32_t format) {
+  BitmapGlyphPtr glyph;
+  BitmapGlyphBuilderPtr builder;
+  builder.Attach(Builder::CreateGlyphBuilder(data, format));
+  if (builder) {
+    glyph.Attach(down_cast<BitmapGlyph*>(builder->Build()));
+  }
+  return glyph;
+}
+
+BitmapGlyph::BitmapGlyph(ReadableFontData* data, int32_t format)
+    : SubTable(data), format_(format) {
+}
+
+/******************************************************************************
+ * BitmapGlyph::Builder class
+ ******************************************************************************/
+BitmapGlyph::Builder::~Builder() {
+}
+
+CALLER_ATTACH BitmapGlyph::Builder*
+BitmapGlyph::Builder::CreateGlyphBuilder(ReadableFontData* data,
+                                         int32_t format) {
+  BitmapGlyphBuilderPtr builder;
+  switch (format) {
+    case 1:
+    case 2:
+    case 3:
+    case 4:
+    case 5:
+    case 6:
+    case 7:
+      builder = new SimpleBitmapGlyph::Builder(data, format);
+      break;
+    case 8:
+    case 9:
+      builder = new CompositeBitmapGlyph::Builder(data, format);
+      break;
+  }
+  return builder.Detach();
+}
+
+BitmapGlyph::Builder::Builder(WritableFontData* data, int32_t format)
+    : SubTable::Builder(data), format_(format) {
+}
+
+BitmapGlyph::Builder::Builder(ReadableFontData* data, int32_t format)
+    : SubTable::Builder(data), format_(format) {
+}
+
+CALLER_ATTACH
+FontDataTable* BitmapGlyph::Builder::SubBuildTable(ReadableFontData* data) {
+  UNREFERENCED_PARAMETER(data);
+  return NULL;
+}
+
+void BitmapGlyph::Builder::SubDataSet() {
+  // NOP
+}
+
+int32_t BitmapGlyph::Builder::SubDataSizeToSerialize() {
+  return InternalReadData()->Length();
+}
+
+bool BitmapGlyph::Builder::SubReadyToSerialize() {
+  return true;
+}
+
+int32_t BitmapGlyph::Builder::SubSerialize(WritableFontData* new_data) {
+  return InternalReadData()->CopyTo(new_data);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph.h b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph.h
new file mode 100644
index 0000000..2dd4c3a
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph.h
@@ -0,0 +1,119 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BITMAP_GLYPH_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BITMAP_GLYPH_H_
+
+#include <vector>
+#include <map>
+
+#include "sfntly/table/subtable.h"
+
+namespace sfntly {
+
+class BitmapGlyph : public SubTable {
+ public:
+  struct Offset {
+    enum {
+      // header
+      kVersion = 0,
+
+      kSmallGlyphMetricsLength = 5,
+      kBigGlyphMetricsLength = 8,
+      // format 1
+      kGlyphFormat1_imageData = kSmallGlyphMetricsLength,
+
+      // format 2
+      kGlyphFormat2_imageData = kSmallGlyphMetricsLength,
+
+      // format 3
+
+      // format 4
+
+      // format 5
+      kGlyphFormat5_imageData = 0,
+
+      // format 6
+      kGlyphFormat6_imageData = kBigGlyphMetricsLength,
+
+      // format 7
+      kGlyphFormat7_imageData = kBigGlyphMetricsLength,
+
+      // format 8
+      kGlyphFormat8_numComponents = kSmallGlyphMetricsLength + 1,
+      kGlyphFormat8_componentArray = kGlyphFormat8_numComponents +
+                                     DataSize::kUSHORT,
+
+      // format 9
+      kGlyphFormat9_numComponents = kBigGlyphMetricsLength,
+      kGlyphFormat9_componentArray = kGlyphFormat9_numComponents +
+                                     DataSize::kUSHORT,
+
+      // ebdtComponent
+      kEbdtComponentLength = DataSize::kUSHORT + 2 * DataSize::kCHAR,
+      kEbdtComponent_glyphCode = 0,
+      kEbdtComponent_xOffset = 2,
+      kEbdtComponent_yOffset = 3,
+    };
+  };
+
+  // TODO(stuartg): builder is not functional at all
+  // - need to add subclasses for each type of bitmap glyph
+  class Builder : public SubTable::Builder {
+   public:
+    virtual ~Builder();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    int32_t format() { return format_; }
+
+    static CALLER_ATTACH Builder* CreateGlyphBuilder(ReadableFontData* data,
+                                                     int32_t format);
+
+   protected:
+    Builder(WritableFontData* data, int32_t format);
+    Builder(ReadableFontData* data, int32_t format);
+
+   private:
+    int32_t format_;
+  };
+
+  virtual ~BitmapGlyph();
+
+  static CALLER_ATTACH BitmapGlyph* CreateGlyph(ReadableFontData* data,
+                                                int32_t format);
+  int32_t format() { return format_; }
+
+  // UNIMPLEMENTED: toString()
+
+ protected:
+  BitmapGlyph(ReadableFontData* data, int32_t format);
+
+ private:
+  int32_t format_;
+};
+typedef Ptr<BitmapGlyph> BitmapGlyphPtr;
+typedef Ptr<BitmapGlyph::Builder> BitmapGlyphBuilderPtr;
+typedef std::map<int32_t, BitmapGlyphBuilderPtr> BitmapGlyphBuilderMap;
+typedef std::vector<BitmapGlyphBuilderMap> BitmapGlyphBuilderList;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BITMAP_GLYPH_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph_info.cc b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph_info.cc
new file mode 100644
index 0000000..a299b3e
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph_info.cc
@@ -0,0 +1,68 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/bitmap_glyph_info.h"
+
+namespace sfntly {
+
+BitmapGlyphInfo::BitmapGlyphInfo(int32_t glyph_id,
+                                 int32_t block_offset,
+                                 int32_t start_offset,
+                                 int32_t length,
+                                 int32_t format)
+    : glyph_id_(glyph_id),
+      relative_(true),
+      block_offset_(block_offset),
+      start_offset_(start_offset),
+      length_(length),
+      format_(format) {
+}
+
+BitmapGlyphInfo::BitmapGlyphInfo(int32_t glyph_id,
+                                 int32_t start_offset,
+                                 int32_t length,
+                                 int32_t format)
+    : glyph_id_(glyph_id),
+      relative_(false),
+      block_offset_(0),
+      start_offset_(start_offset),
+      length_(length),
+      format_(format) {
+}
+
+bool BitmapGlyphInfo::operator==(const BitmapGlyphInfo& rhs) const {
+  return (format_ == rhs.format_ &&
+          glyph_id_ == rhs.glyph_id_ &&
+          length_ == rhs.length_ &&
+          offset() == rhs.offset());
+}
+
+bool BitmapGlyphInfo::operator==(BitmapGlyphInfo* rhs) {
+  if (rhs == NULL) {
+    return false;  // Well defined C++ code's this is always not null.
+  }
+  return (format_ == rhs->format() &&
+          glyph_id_ == rhs->glyph_id() &&
+          length_ == rhs->length() &&
+          offset() == rhs->offset());
+}
+
+bool StartOffsetComparator::operator()(BitmapGlyphInfo* lhs,
+                                       BitmapGlyphInfo* rhs) {
+  return lhs->start_offset() > rhs->start_offset();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph_info.h b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph_info.h
new file mode 100644
index 0000000..9921d0d
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_glyph_info.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_GLYPH_INFO_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_GLYPH_INFO_H_
+
+#include <vector>
+#include <map>
+
+#include "sfntly/table/subtable.h"
+
+namespace sfntly {
+
+// An immutable class holding bitmap glyph information.
+class BitmapGlyphInfo : public RefCounted<BitmapGlyphInfo> {
+ public:
+  // Constructor for a relative located glyph. The glyph's position in the EBDT
+  // table is a combination of it's block offset and it's own start offset.
+  // @param glyphId the glyph id
+  // @param blockOffset the offset of the block to which the glyph belongs
+  // @param startOffset the offset of the glyph within the block
+  // @param length the byte length
+  // @param format the glyph image format
+  BitmapGlyphInfo(int32_t glyph_id,
+                  int32_t block_offset,
+                  int32_t start_offset,
+                  int32_t length,
+                  int32_t format);
+
+  // Constructor for an absolute located glyph. The glyph's position in the EBDT
+  // table is only given by it's own start offset.
+  // @param glyphId the glyph id
+  // @param startOffset the offset of the glyph within the block
+  // @param length the byte length
+  // @param format the glyph image format
+  BitmapGlyphInfo(int32_t glyph_id,
+                  int32_t start_offset,
+                  int32_t length,
+                  int32_t format);
+
+  int32_t glyph_id() const { return glyph_id_; }
+  bool relative() const { return relative_; }
+  int32_t block_offset() const { return block_offset_; }
+  int32_t offset() const { return block_offset() + start_offset(); }
+  int32_t start_offset() const { return start_offset_; }
+  int32_t length() const { return length_; }
+  int32_t format() const { return format_; }
+
+  // UNIMPLEMENTED: hashCode()
+  bool operator==(const BitmapGlyphInfo& rhs) const;
+  bool operator==(BitmapGlyphInfo* rhs);
+
+ private:
+  int32_t glyph_id_;
+  bool relative_;
+  int32_t block_offset_;
+  int32_t start_offset_;
+  int32_t length_;
+  int32_t format_;
+};
+typedef Ptr<BitmapGlyphInfo> BitmapGlyphInfoPtr;
+typedef std::map<int32_t, BitmapGlyphInfoPtr> BitmapGlyphInfoMap;
+typedef std::vector<BitmapGlyphInfoMap> BitmapLocaList;
+
+class StartOffsetComparator {
+ public:
+  bool operator()(BitmapGlyphInfo* lhs, BitmapGlyphInfo* rhs);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_GLYPH_INFO_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/bitmap_size_table.cc b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_size_table.cc
new file mode 100644
index 0000000..6c7d731
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_size_table.cc
@@ -0,0 +1,604 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/bitmap_size_table.h"
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "sfntly/math/font_math.h"
+#include "sfntly/table/bitmap/eblc_table.h"
+#include "sfntly/table/bitmap/index_sub_table_format1.h"
+#include "sfntly/table/bitmap/index_sub_table_format2.h"
+#include "sfntly/table/bitmap/index_sub_table_format3.h"
+#include "sfntly/table/bitmap/index_sub_table_format4.h"
+#include "sfntly/table/bitmap/index_sub_table_format5.h"
+
+namespace sfntly {
+/******************************************************************************
+ * BitmapSizeTable class
+ ******************************************************************************/
+BitmapSizeTable::~BitmapSizeTable() {
+}
+
+int32_t BitmapSizeTable::IndexSubTableArrayOffset() {
+  return data_->ReadULongAsInt(
+      EblcTable::Offset::kBitmapSizeTable_indexSubTableArrayOffset);
+}
+
+int32_t BitmapSizeTable::IndexTableSize() {
+  return data_->ReadULongAsInt(
+      EblcTable::Offset::kBitmapSizeTable_indexTableSize);
+}
+
+int32_t BitmapSizeTable::NumberOfIndexSubTables() {
+  return NumberOfIndexSubTables(data_, 0);
+}
+
+int32_t BitmapSizeTable::ColorRef() {
+  return data_->ReadULongAsInt(EblcTable::Offset::kBitmapSizeTable_colorRef);
+}
+
+int32_t BitmapSizeTable::StartGlyphIndex() {
+  return data_->ReadUShort(EblcTable::Offset::kBitmapSizeTable_startGlyphIndex);
+}
+
+int32_t BitmapSizeTable::EndGlyphIndex() {
+  return data_->ReadUShort(EblcTable::Offset::kBitmapSizeTable_endGlyphIndex);
+}
+
+int32_t BitmapSizeTable::PpemX() {
+  return data_->ReadByte(EblcTable::Offset::kBitmapSizeTable_ppemX);
+}
+
+int32_t BitmapSizeTable::PpemY() {
+  return data_->ReadByte(EblcTable::Offset::kBitmapSizeTable_ppemY);
+}
+
+int32_t BitmapSizeTable::BitDepth() {
+  return data_->ReadByte(EblcTable::Offset::kBitmapSizeTable_bitDepth);
+}
+
+int32_t BitmapSizeTable::FlagsAsInt() {
+  return data_->ReadChar(EblcTable::Offset::kBitmapSizeTable_flags);
+}
+
+IndexSubTable* BitmapSizeTable::GetIndexSubTable(int32_t index) {
+  IndexSubTableList* subtable_list = GetIndexSubTableList();
+  if (index >= 0 && (size_t)index < subtable_list->size()) {
+    return (*subtable_list)[index];
+  }
+  return NULL;
+}
+
+int32_t BitmapSizeTable::GlyphOffset(int32_t glyph_id) {
+  IndexSubTable* subtable = SearchIndexSubTables(glyph_id);
+  if (subtable == NULL) {
+    return -1;
+  }
+  return subtable->GlyphOffset(glyph_id);
+}
+
+int32_t BitmapSizeTable::GlyphLength(int32_t glyph_id) {
+  IndexSubTable* subtable = SearchIndexSubTables(glyph_id);
+  if (subtable == NULL) {
+    return -1;
+  }
+  return subtable->GlyphLength(glyph_id);
+}
+
+CALLER_ATTACH BitmapGlyphInfo* BitmapSizeTable::GlyphInfo(int32_t glyph_id) {
+  IndexSubTable* sub_table = SearchIndexSubTables(glyph_id);
+  if (sub_table == NULL) {
+    return NULL;
+  }
+  return sub_table->GlyphInfo(glyph_id);
+}
+
+int32_t BitmapSizeTable::GlyphFormat(int32_t glyph_id) {
+  IndexSubTable* subtable = SearchIndexSubTables(glyph_id);
+  if (subtable == NULL) {
+    return -1;
+  }
+  return subtable->image_format();
+}
+
+BitmapSizeTable::BitmapSizeTable(ReadableFontData* data,
+                                 ReadableFontData* master_data)
+    : SubTable(data, master_data) {
+}
+
+// static
+int32_t BitmapSizeTable::NumberOfIndexSubTables(ReadableFontData* data,
+                                                int32_t table_offset) {
+  return data->ReadULongAsInt(table_offset +
+      EblcTable::Offset::kBitmapSizeTable_numberOfIndexSubTables);
+}
+
+IndexSubTable* BitmapSizeTable::SearchIndexSubTables(int32_t glyph_id) {
+  // would be faster to binary search but too many size tables don't have
+  // sorted subtables
+#if (SFNTLY_BITMAPSIZE_USE_BINARY_SEARCH)
+  return BinarySearchIndexSubTables(glyph_id);
+#else
+  return LinearSearchIndexSubTables(glyph_id);
+#endif
+}
+
+IndexSubTable* BitmapSizeTable::LinearSearchIndexSubTables(int32_t glyph_id) {
+  IndexSubTableList* subtable_list = GetIndexSubTableList();
+  for (IndexSubTableList::iterator b = subtable_list->begin(),
+                                   e = subtable_list->end(); b != e; b++) {
+    if ((*b)->first_glyph_index() <= glyph_id &&
+        (*b)->last_glyph_index() >= glyph_id) {
+      return *b;
+    }
+  }
+  return NULL;
+}
+
+IndexSubTable* BitmapSizeTable::BinarySearchIndexSubTables(int32_t glyph_id) {
+  IndexSubTableList* subtable_list = GetIndexSubTableList();
+  int32_t index = 0;
+  int32_t bottom = 0;
+  int32_t top = subtable_list->size();
+  while (top != bottom) {
+    index = (top + bottom) / 2;
+    IndexSubTable* subtable = (*subtable_list)[index];
+    if (glyph_id < subtable->first_glyph_index()) {
+      // Location beow current location
+      top = index;
+    } else {
+      if (glyph_id <= subtable->last_glyph_index()) {
+        return subtable;
+      } else {
+        bottom = index + 1;
+      }
+    }
+  }
+  return NULL;
+}
+
+CALLER_ATTACH
+IndexSubTable* BitmapSizeTable::CreateIndexSubTable(int32_t index) {
+  return IndexSubTable::CreateIndexSubTable(master_read_data(),
+                                            IndexSubTableArrayOffset(),
+                                            index);
+}
+
+IndexSubTableList* BitmapSizeTable::GetIndexSubTableList() {
+  AutoLock lock(index_subtables_lock_);
+  if (index_subtables_.empty()) {
+    for (int32_t i = 0; i < NumberOfIndexSubTables(); ++i) {
+      IndexSubTablePtr table;
+      table.Attach(CreateIndexSubTable(i));
+      index_subtables_.push_back(table);
+    }
+  }
+  return &index_subtables_;
+}
+
+/******************************************************************************
+ * BitmapSizeTable::Builder class
+ ******************************************************************************/
+BitmapSizeTable::Builder::~Builder() {
+}
+
+CALLER_ATTACH
+FontDataTable* BitmapSizeTable::Builder::SubBuildTable(ReadableFontData* data) {
+  BitmapSizeTablePtr output = new BitmapSizeTable(data, master_read_data());
+  return output.Detach();
+}
+
+void BitmapSizeTable::Builder::SubDataSet() {
+  Revert();
+}
+
+int32_t BitmapSizeTable::Builder::SubDataSizeToSerialize() {
+  IndexSubTableBuilderList* builders = IndexSubTableBuilders();
+  if (builders->empty()) {
+    return 0;
+  }
+  int32_t size = EblcTable::Offset::kBitmapSizeTableLength;
+  bool variable = false;
+  for (IndexSubTableBuilderList::iterator b = builders->begin(),
+                                          e = builders->end(); b != e; b++) {
+    size += EblcTable::Offset::kIndexSubTableEntryLength;
+    int32_t sub_table_size = (*b)->SubDataSizeToSerialize();
+    int32_t padding = FontMath::PaddingRequired(abs(sub_table_size),
+                                                DataSize::kULONG);
+#if defined (SFNTLY_DEBUG_BITMAP)
+    fprintf(stderr, "subtable size=%d\n", sub_table_size);
+#endif
+    variable = (sub_table_size > 0) ? variable : true;
+    size += abs(sub_table_size) + padding;
+  }
+#if defined (SFNTLY_DEBUG_BITMAP)
+  fprintf(stderr, "bitmap table size=%d\n", variable ? -size : size);
+#endif
+  return variable ? -size : size;
+}
+
+bool BitmapSizeTable::Builder::SubReadyToSerialize() {
+  if (IndexSubTableBuilders()->empty()) {
+    return false;
+  }
+  return true;
+}
+
+int32_t BitmapSizeTable::Builder::SubSerialize(WritableFontData* new_data) {
+  SetNumberOfIndexSubTables(IndexSubTableBuilders()->size());
+  int32_t size = InternalReadData()->CopyTo(new_data);
+  return size;
+}
+
+CALLER_ATTACH BitmapSizeTable::Builder*
+BitmapSizeTable::Builder::CreateBuilder(WritableFontData* data,
+                                        ReadableFontData* master_data) {
+  BitmapSizeTableBuilderPtr output =
+      new BitmapSizeTable::Builder(data, master_data);
+  return output.Detach();
+}
+
+CALLER_ATTACH BitmapSizeTable::Builder*
+BitmapSizeTable::Builder::CreateBuilder(ReadableFontData* data,
+                                        ReadableFontData* master_data) {
+  BitmapSizeTableBuilderPtr output =
+      new BitmapSizeTable::Builder(data, master_data);
+  return output.Detach();
+}
+
+int32_t BitmapSizeTable::Builder::IndexSubTableArrayOffset() {
+  return InternalReadData()->ReadULongAsInt(
+      EblcTable::Offset::kBitmapSizeTable_indexSubTableArrayOffset);
+}
+
+void BitmapSizeTable::Builder::SetIndexSubTableArrayOffset(int32_t offset) {
+  InternalWriteData()->WriteULong(
+      EblcTable::Offset::kBitmapSizeTable_indexSubTableArrayOffset, offset);
+}
+
+int32_t BitmapSizeTable::Builder::IndexTableSize() {
+  return InternalReadData()->ReadULongAsInt(
+      EblcTable::Offset::kBitmapSizeTable_indexTableSize);
+}
+
+void BitmapSizeTable::Builder::SetIndexTableSize(int32_t size) {
+  InternalWriteData()->WriteULong(
+      EblcTable::Offset::kBitmapSizeTable_indexTableSize, size);
+}
+
+int32_t BitmapSizeTable::Builder::NumberOfIndexSubTables() {
+  return GetIndexSubTableBuilders()->size();
+}
+
+int32_t BitmapSizeTable::Builder::ColorRef() {
+  return InternalReadData()->ReadULongAsInt(
+      EblcTable::Offset::kBitmapSizeTable_colorRef);
+}
+
+int32_t BitmapSizeTable::Builder::StartGlyphIndex() {
+  return InternalReadData()->ReadUShort(
+      EblcTable::Offset::kBitmapSizeTable_startGlyphIndex);
+}
+
+int32_t BitmapSizeTable::Builder::EndGlyphIndex() {
+  return InternalReadData()->ReadUShort(
+      EblcTable::Offset::kBitmapSizeTable_endGlyphIndex);
+}
+
+int32_t BitmapSizeTable::Builder::PpemX() {
+  return InternalReadData()->ReadByte(
+      EblcTable::Offset::kBitmapSizeTable_ppemX);
+}
+
+int32_t BitmapSizeTable::Builder::PpemY() {
+  return InternalReadData()->ReadByte(
+      EblcTable::Offset::kBitmapSizeTable_ppemY);
+}
+
+int32_t BitmapSizeTable::Builder::BitDepth() {
+  return InternalReadData()->ReadByte(
+      EblcTable::Offset::kBitmapSizeTable_bitDepth);
+}
+
+int32_t BitmapSizeTable::Builder::FlagsAsInt() {
+  return InternalReadData()->ReadChar(
+      EblcTable::Offset::kBitmapSizeTable_flags);
+}
+
+IndexSubTable::Builder* BitmapSizeTable::Builder::IndexSubTableBuilder(
+    int32_t index) {
+  IndexSubTableBuilderList* sub_table_list = GetIndexSubTableBuilders();
+  return sub_table_list->at(index);
+}
+
+CALLER_ATTACH BitmapGlyphInfo* BitmapSizeTable::Builder::GlyphInfo(
+    int32_t glyph_id) {
+  IndexSubTable::Builder* sub_table = SearchIndexSubTables(glyph_id);
+  if (sub_table == NULL) {
+    return NULL;
+  }
+  return sub_table->GlyphInfo(glyph_id);
+}
+
+int32_t BitmapSizeTable::Builder::GlyphOffset(int32_t glyph_id) {
+  IndexSubTable::Builder* subtable = SearchIndexSubTables(glyph_id);
+  if (subtable == NULL) {
+    return -1;
+  }
+  return subtable->GlyphOffset(glyph_id);
+}
+
+int32_t BitmapSizeTable::Builder::GlyphLength(int32_t glyph_id) {
+  IndexSubTable::Builder* subtable = SearchIndexSubTables(glyph_id);
+  if (subtable == NULL) {
+    return -1;
+  }
+  return subtable->GlyphLength(glyph_id);
+}
+
+int32_t BitmapSizeTable::Builder::GlyphFormat(int32_t glyph_id) {
+  IndexSubTable::Builder* subtable = SearchIndexSubTables(glyph_id);
+  if (subtable == NULL) {
+    return -1;
+  }
+  return subtable->image_format();
+}
+
+IndexSubTableBuilderList* BitmapSizeTable::Builder::IndexSubTableBuilders() {
+  return GetIndexSubTableBuilders();
+}
+
+CALLER_ATTACH BitmapSizeTable::Builder::BitmapGlyphInfoIterator*
+BitmapSizeTable::Builder::GetIterator() {
+  Ptr<BitmapSizeTable::Builder::BitmapGlyphInfoIterator> output =
+      new BitmapSizeTable::Builder::BitmapGlyphInfoIterator(this);
+  return output.Detach();
+}
+
+void BitmapSizeTable::Builder::GenerateLocaMap(BitmapGlyphInfoMap* output) {
+  assert(output);
+  Ptr<BitmapSizeTable::Builder::BitmapGlyphInfoIterator> it;
+  it.Attach(GetIterator());
+  while (it->HasNext()) {
+    BitmapGlyphInfoPtr info;
+    info.Attach(it->Next());
+    (*output)[info->glyph_id()] = info;
+  }
+}
+
+void BitmapSizeTable::Builder::Revert() {
+  index_sub_tables_.clear();
+  set_model_changed(false);
+}
+
+BitmapSizeTable::Builder::Builder(WritableFontData* data,
+                                  ReadableFontData* master_data)
+    : SubTable::Builder(data, master_data) {
+}
+
+BitmapSizeTable::Builder::Builder(ReadableFontData* data,
+                                  ReadableFontData* master_data)
+    : SubTable::Builder(data, master_data) {
+}
+
+void BitmapSizeTable::Builder::SetNumberOfIndexSubTables(int32_t count) {
+  InternalWriteData()->WriteULong(
+      EblcTable::Offset::kBitmapSizeTable_numberOfIndexSubTables, count);
+}
+
+IndexSubTable::Builder* BitmapSizeTable::Builder::SearchIndexSubTables(
+    int32_t glyph_id) {
+  // would be faster to binary search but too many size tables don't have
+  // sorted subtables
+#if (SFNTLY_BITMAPSIZE_USE_BINARY_SEARCH)
+  return BinarySearchIndexSubTables(glyph_id);
+#else
+  return LinearSearchIndexSubTables(glyph_id);
+#endif
+}
+
+IndexSubTable::Builder* BitmapSizeTable::Builder::LinearSearchIndexSubTables(
+    int32_t glyph_id) {
+  IndexSubTableBuilderList* subtable_list = GetIndexSubTableBuilders();
+  for (IndexSubTableBuilderList::iterator b = subtable_list->begin(),
+                                          e = subtable_list->end();
+                                          b != e; b++) {
+    if ((*b)->first_glyph_index() <= glyph_id &&
+        (*b)->last_glyph_index() >= glyph_id) {
+      return *b;
+    }
+  }
+  return NULL;
+}
+
+IndexSubTable::Builder* BitmapSizeTable::Builder::BinarySearchIndexSubTables(
+    int32_t glyph_id) {
+  IndexSubTableBuilderList* subtable_list = GetIndexSubTableBuilders();
+  int32_t index = 0;
+  int32_t bottom = 0;
+  int32_t top = subtable_list->size();
+  while (top != bottom) {
+    index = (top + bottom) / 2;
+    IndexSubTable::Builder* subtable = subtable_list->at(index);
+    if (glyph_id < subtable->first_glyph_index()) {
+      // Location beow current location
+      top = index;
+    } else {
+      if (glyph_id <= subtable->last_glyph_index()) {
+        return subtable;
+      } else {
+        bottom = index + 1;
+      }
+    }
+  }
+  return NULL;
+}
+
+IndexSubTableBuilderList* BitmapSizeTable::Builder::GetIndexSubTableBuilders() {
+  if (index_sub_tables_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &index_sub_tables_;
+}
+
+void BitmapSizeTable::Builder::Initialize(ReadableFontData* data) {
+  index_sub_tables_.clear();
+  if (data) {
+    int32_t number_of_index_subtables =
+        BitmapSizeTable::NumberOfIndexSubTables(data, 0);
+    index_sub_tables_.resize(number_of_index_subtables);
+    for (int32_t i = 0; i < number_of_index_subtables; ++i) {
+      index_sub_tables_[i].Attach(CreateIndexSubTableBuilder(i));
+    }
+  }
+}
+
+CALLER_ATTACH IndexSubTable::Builder*
+BitmapSizeTable::Builder::CreateIndexSubTableBuilder(int32_t index) {
+  return IndexSubTable::Builder::CreateBuilder(master_read_data(),
+                                               IndexSubTableArrayOffset(),
+                                               index);
+}
+
+/******************************************************************************
+ * BitmapSizeTable::Builder::BitmapGlyphInfoIterator class
+ ******************************************************************************/
+BitmapSizeTable::Builder::BitmapGlyphInfoIterator::BitmapGlyphInfoIterator(
+    BitmapSizeTable::Builder* container)
+    : RefIterator<BitmapGlyphInfo, BitmapSizeTable::Builder>(container) {
+  sub_table_iter_ = container->IndexSubTableBuilders()->begin();
+  sub_table_glyph_info_iter_.Attach((*sub_table_iter_)->GetIterator());
+}
+
+bool BitmapSizeTable::Builder::BitmapGlyphInfoIterator::HasNext() {
+  if (sub_table_glyph_info_iter_ && HasNext(sub_table_glyph_info_iter_)) {
+    return true;
+  }
+  while (++sub_table_iter_ != container()->IndexSubTableBuilders()->end()) {
+    sub_table_glyph_info_iter_.Attach((*sub_table_iter_)->GetIterator());
+    if (HasNext(sub_table_glyph_info_iter_)) {
+      return true;
+    }
+  }
+  return false;
+}
+
+CALLER_ATTACH
+BitmapGlyphInfo* BitmapSizeTable::Builder::BitmapGlyphInfoIterator::Next() {
+  if (!HasNext()) {
+    // Note: In C++, we do not throw exception when there's no element.
+    return NULL;
+  }
+  return Next(sub_table_glyph_info_iter_);
+}
+
+bool BitmapSizeTable::Builder::BitmapGlyphInfoIterator::HasNext(
+    BitmapGlyphInfoIter* iterator_base) {
+  if (iterator_base) {
+    switch (iterator_base->container_base()->index_format()) {
+      case 1: {
+        IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->HasNext();
+      }
+
+      case 2: {
+        IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->HasNext();
+      }
+
+      case 3: {
+        IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->HasNext();
+      }
+
+      case 4: {
+        IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->HasNext();
+      }
+
+      case 5: {
+        IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->HasNext();
+      }
+
+      default:
+        break;
+    }
+  }
+  return false;
+}
+
+CALLER_ATTACH
+BitmapGlyphInfo* BitmapSizeTable::Builder::BitmapGlyphInfoIterator::Next(
+    BitmapGlyphInfoIter* iterator_base) {
+  if (iterator_base) {
+    switch (iterator_base->container_base()->index_format()) {
+      case 1: {
+        IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->Next();
+      }
+
+      case 2: {
+        IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->Next();
+      }
+
+      case 3: {
+        IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->Next();
+      }
+
+      case 4: {
+        IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->Next();
+      }
+
+      case 5: {
+        IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator* it =
+            down_cast<IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator*>(
+                iterator_base);
+        return it->Next();
+      }
+
+      default:
+        break;
+    }
+  }
+  return NULL;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/bitmap_size_table.h b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_size_table.h
new file mode 100644
index 0000000..6733e20
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/bitmap_size_table.h
@@ -0,0 +1,173 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BITMAP_SIZE_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BITMAP_SIZE_TABLE_H_
+
+#include "sfntly/port/lock.h"
+#include "sfntly/table/bitmap/bitmap_glyph_info.h"
+#include "sfntly/table/bitmap/index_sub_table.h"
+
+namespace sfntly {
+// Binary search would be faster but many fonts have index subtables that
+// aren't sorted.
+// Note: preprocessor define is used to avoid const expression warnings in C++
+//       code.
+#define SFNTLY_BITMAPSIZE_USE_BINARY_SEARCH 0
+
+class BitmapSizeTable : public SubTable,
+                        public RefCounted<BitmapSizeTable> {
+ public:
+  class Builder : public SubTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    class BitmapGlyphInfoIterator :
+        public RefIterator<BitmapGlyphInfo, Builder> {
+     public:
+      explicit BitmapGlyphInfoIterator(Builder* container);
+      virtual ~BitmapGlyphInfoIterator() {}
+
+      virtual bool HasNext();
+      CALLER_ATTACH virtual BitmapGlyphInfo* Next();
+
+     private:
+      bool HasNext(BitmapGlyphInfoIter* iterator_base);
+      CALLER_ATTACH BitmapGlyphInfo* Next(BitmapGlyphInfoIter* iterator_base);
+
+      IndexSubTableBuilderList::iterator sub_table_iter_;
+      BitmapGlyphInfoIterPtr sub_table_glyph_info_iter_;
+    };
+
+    virtual ~Builder();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    static CALLER_ATTACH Builder* CreateBuilder(WritableFontData* data,
+                                                ReadableFontData* master_data);
+    static CALLER_ATTACH Builder* CreateBuilder(ReadableFontData* data,
+                                                ReadableFontData* master_data);
+    // Gets the subtable array offset as set in the original table as read from
+    // the font file. This value cannot be explicitly set and will be generated
+    // during table building.
+    // @return the subtable array offset
+    int32_t IndexSubTableArrayOffset();
+
+    // Sets the subtable array offset. This is used only during the building
+    // process when the objects are being serialized.
+    // @param offset the offset to the index subtable array
+    void SetIndexSubTableArrayOffset(int32_t offset);
+
+    // Gets the subtable array size as set in the original table as read from
+    // the font file. This value cannot be explicitly set and will be generated
+    // during table building.
+    // @return the subtable array size
+    int32_t IndexTableSize();
+
+    // Sets the subtable size. This is used only during the building process
+    // when the objects are being serialized.
+    // @param size the offset to the index subtable array
+    void SetIndexTableSize(int32_t size);
+
+    int32_t NumberOfIndexSubTables();
+    int32_t ColorRef();
+    // TODO(stuartg): SBitLineMetrics hori();
+    // TODO(stuartg): SBitLineMetrics vert();
+    int32_t StartGlyphIndex();
+    int32_t EndGlyphIndex();
+    int32_t PpemX();
+    int32_t PpemY();
+    int32_t BitDepth();
+    int32_t FlagsAsInt();
+
+    IndexSubTable::Builder* IndexSubTableBuilder(int32_t index);
+    CALLER_ATTACH BitmapGlyphInfo* GlyphInfo(int32_t glyph_id);
+    int32_t GlyphOffset(int32_t glyph_id);
+    int32_t GlyphLength(int32_t glyph_id);
+    int32_t GlyphFormat(int32_t glyph_id);
+    IndexSubTableBuilderList* IndexSubTableBuilders();
+    // Note: renamed from iterator(), type is the derived type.
+    CALLER_ATTACH BitmapGlyphInfoIterator* GetIterator();
+    void GenerateLocaMap(BitmapGlyphInfoMap* output);
+
+   protected:
+    void Revert();
+
+   private:
+    Builder(WritableFontData* data, ReadableFontData* master_data);
+    Builder(ReadableFontData* data, ReadableFontData* master_data);
+
+    void SetNumberOfIndexSubTables(int32_t count);
+    IndexSubTable::Builder* SearchIndexSubTables(int32_t glyph_id);
+    IndexSubTable::Builder* LinearSearchIndexSubTables(int32_t glyph_id);
+    IndexSubTable::Builder* BinarySearchIndexSubTables(int32_t glyph_id);
+    IndexSubTableBuilderList* GetIndexSubTableBuilders();
+    void Initialize(ReadableFontData* data);
+    CALLER_ATTACH IndexSubTable::Builder* CreateIndexSubTableBuilder(
+        int32_t index);
+
+    IndexSubTableBuilderList index_sub_tables_;
+  };
+
+  virtual ~BitmapSizeTable();
+
+  int32_t IndexSubTableArrayOffset();
+  int32_t IndexTableSize();
+  int32_t NumberOfIndexSubTables();
+  int32_t ColorRef();
+  // TODO(stuartg): SBitLineMetrics hori();
+  // TODO(stuartg): SBitLineMetrics vert();
+  int32_t StartGlyphIndex();
+  int32_t EndGlyphIndex();
+  int32_t PpemX();
+  int32_t PpemY();
+  int32_t BitDepth();
+  int32_t FlagsAsInt();
+
+  // Note: renamed from indexSubTable()
+  IndexSubTable* GetIndexSubTable(int32_t index);
+  int32_t GlyphOffset(int32_t glyph_id);
+  int32_t GlyphLength(int32_t glyph_id);
+  CALLER_ATTACH BitmapGlyphInfo* GlyphInfo(int32_t glyph_id);
+  int32_t GlyphFormat(int32_t glyph_id);
+
+ protected:
+  BitmapSizeTable(ReadableFontData* data,
+                  ReadableFontData* master_data);
+
+ private:
+  static int32_t NumberOfIndexSubTables(ReadableFontData* data,
+                                        int32_t table_offset);
+  IndexSubTable* SearchIndexSubTables(int32_t glyph_id);
+  IndexSubTable* LinearSearchIndexSubTables(int32_t glyph_id);
+  IndexSubTable* BinarySearchIndexSubTables(int32_t glyph_id);
+  CALLER_ATTACH IndexSubTable* CreateIndexSubTable(int32_t index);
+  IndexSubTableList* GetIndexSubTableList();
+
+  Lock index_subtables_lock_;
+  IndexSubTableList index_subtables_;
+};
+typedef Ptr<BitmapSizeTable> BitmapSizeTablePtr;
+typedef std::vector<BitmapSizeTablePtr> BitmapSizeTableList;
+typedef Ptr<BitmapSizeTable::Builder> BitmapSizeTableBuilderPtr;
+typedef std::vector<BitmapSizeTableBuilderPtr> BitmapSizeTableBuilderList;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_BITMAP_SIZE_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/composite_bitmap_glyph.cc b/sfntly/cpp/src/sfntly/table/bitmap/composite_bitmap_glyph.cc
new file mode 100644
index 0000000..ae7dc5a
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/composite_bitmap_glyph.cc
@@ -0,0 +1,109 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/composite_bitmap_glyph.h"
+
+namespace sfntly {
+/******************************************************************************
+ * CompositeBitmapGlyph class
+ ******************************************************************************/
+CompositeBitmapGlyph::CompositeBitmapGlyph(ReadableFontData* data,
+                                           int32_t format)
+    : BitmapGlyph(data, format) {
+  Initialize(format);
+}
+
+CompositeBitmapGlyph::~CompositeBitmapGlyph() {
+}
+
+int32_t CompositeBitmapGlyph::NumComponents() {
+  return data_->ReadUShort(num_components_offset_);
+}
+
+CompositeBitmapGlyph::Component CompositeBitmapGlyph::GetComponent(
+    int32_t component_num) const {
+  int32_t component_offset = component_array_offset_ +
+                             component_num * Offset::kEbdtComponentLength;
+  return CompositeBitmapGlyph::Component(
+      data_->ReadUShort(component_offset + Offset::kEbdtComponent_glyphCode),
+      data_->ReadChar(component_offset + Offset::kEbdtComponent_xOffset),
+      data_->ReadChar(component_offset + Offset::kEbdtComponent_yOffset));
+}
+
+void CompositeBitmapGlyph::Initialize(int32_t format) {
+  if (format == 8) {
+    num_components_offset_ = Offset::kGlyphFormat8_numComponents;
+    component_array_offset_ = Offset::kGlyphFormat8_componentArray;
+  } else if (format == 9) {
+    num_components_offset_ = Offset::kGlyphFormat9_numComponents;
+    component_array_offset_ = Offset::kGlyphFormat9_componentArray;
+  } else {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IllegalStateException("Attempt to create a Composite Bitmap Glyph "
+                                "with a non-composite format.");
+#endif
+  }
+}
+
+/******************************************************************************
+ * CompositeBitmapGlyph::Component class
+ ******************************************************************************/
+CompositeBitmapGlyph::Component::Component(const Component& rhs)
+    : glyph_code_(rhs.glyph_code_),
+      x_offset_(rhs.x_offset_),
+      y_offset_(rhs.y_offset_) {
+}
+
+bool CompositeBitmapGlyph::Component::operator==(
+    const CompositeBitmapGlyph::Component& rhs) {
+  return glyph_code_ == rhs.glyph_code_;
+}
+
+CompositeBitmapGlyph::Component& CompositeBitmapGlyph::Component::operator=(
+    const CompositeBitmapGlyph::Component& rhs) {
+  glyph_code_ = rhs.glyph_code_;
+  x_offset_ = rhs.x_offset_;
+  y_offset_ = rhs.y_offset_;
+  return *this;
+}
+
+CompositeBitmapGlyph::Component::Component(int32_t glyph_code,
+                                           int32_t x_offset,
+                                           int32_t y_offset)
+    : glyph_code_(glyph_code), x_offset_(x_offset), y_offset_(y_offset) {
+}
+
+/******************************************************************************
+ * CompositeBitmapGlyph::Builder class
+ ******************************************************************************/
+CompositeBitmapGlyph::Builder::Builder(ReadableFontData* data, int32_t format)
+    : BitmapGlyph::Builder(data, format) {
+}
+
+CompositeBitmapGlyph::Builder::Builder(WritableFontData* data, int32_t format)
+    : BitmapGlyph::Builder(data, format) {
+}
+
+CompositeBitmapGlyph::Builder::~Builder() {
+}
+
+CALLER_ATTACH FontDataTable*
+CompositeBitmapGlyph::Builder::SubBuildTable(ReadableFontData* data) {
+  Ptr<CompositeBitmapGlyph> glyph = new CompositeBitmapGlyph(data, format());
+  return glyph.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/composite_bitmap_glyph.h b/sfntly/cpp/src/sfntly/table/bitmap/composite_bitmap_glyph.h
new file mode 100644
index 0000000..897db7e
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/composite_bitmap_glyph.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_COMPOSITE_BITMAP_GLYPH_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_COMPOSITE_BITMAP_GLYPH_H_
+
+#include "sfntly/table/bitmap/bitmap_glyph.h"
+
+namespace sfntly {
+
+class CompositeBitmapGlyph : public BitmapGlyph,
+                             public RefCounted<CompositeBitmapGlyph> {
+ public:
+  class Component {
+   public:
+    Component(const Component& rhs);
+
+    int32_t glyph_code() { return glyph_code_; }
+    int32_t x_offset() { return x_offset_; }
+    int32_t y_offset() { return y_offset_; }
+
+    // UNIMPLEMENTED: int hashCode()
+    bool operator==(const Component& rhs);
+    Component& operator=(const Component& rhs);
+
+   protected:
+    Component(int32_t glyph_code, int32_t x_offset, int32_t y_offset);
+
+   private:
+    int32_t glyph_code_;
+    int32_t x_offset_;
+    int32_t y_offset_;
+
+    friend class CompositeBitmapGlyph;
+  };
+
+  class Builder : public BitmapGlyph::Builder,
+                  public RefCounted<Builder> {
+   public:
+    Builder(WritableFontData* data, int32_t format);
+    Builder(ReadableFontData* data, int32_t format);
+    virtual ~Builder();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+  };
+
+  CompositeBitmapGlyph(ReadableFontData* data, int32_t format);
+  virtual ~CompositeBitmapGlyph();
+  int32_t NumComponents();
+  // Note: returned immutable object over stack.
+  Component GetComponent(int32_t component_num) const;
+
+ private:
+  void Initialize(int32_t format);
+
+  int32_t num_components_offset_;
+  int32_t component_array_offset_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_COMPOSITE_BITMAP_GLYPH_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/ebdt_table.cc b/sfntly/cpp/src/sfntly/table/bitmap/ebdt_table.cc
new file mode 100644
index 0000000..eeb1fa0
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/ebdt_table.cc
@@ -0,0 +1,236 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/ebdt_table.h"
+
+#include <stdlib.h>
+
+#include "sfntly/table/bitmap/composite_bitmap_glyph.h"
+#include "sfntly/table/bitmap/simple_bitmap_glyph.h"
+
+namespace sfntly {
+/******************************************************************************
+ * EbdtTable class
+ ******************************************************************************/
+EbdtTable::~EbdtTable() {
+}
+
+int32_t EbdtTable::Version() {
+  return data_->ReadFixed(Offset::kVersion);
+}
+
+CALLER_ATTACH
+BitmapGlyph* EbdtTable::Glyph(int32_t offset, int32_t length, int32_t format) {
+  ReadableFontDataPtr glyph_data;
+  glyph_data.Attach(down_cast<ReadableFontData*>(data_->Slice(offset, length)));
+  return BitmapGlyph::CreateGlyph(glyph_data, format);
+}
+
+EbdtTable::EbdtTable(Header* header, ReadableFontData* data)
+    : SubTableContainerTable(header, data) {
+}
+
+/******************************************************************************
+ * EbdtTable::Builder class
+ ******************************************************************************/
+EbdtTable::Builder::Builder(Header* header, WritableFontData* data)
+  : SubTableContainerTable::Builder(header, data) {
+}
+
+EbdtTable::Builder::Builder(Header* header, ReadableFontData* data)
+  : SubTableContainerTable::Builder(header, data) {
+}
+
+EbdtTable::Builder::~Builder() {
+}
+
+CALLER_ATTACH FontDataTable*
+    EbdtTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new EbdtTable(header(), data);
+  return table.Detach();
+}
+
+void EbdtTable::Builder::SubDataSet() {
+  Revert();
+}
+
+int32_t EbdtTable::Builder::SubDataSizeToSerialize() {
+  if (glyph_builders_.empty()) {
+    return 0;
+  }
+  bool fixed = true;
+  int32_t size = Offset::kHeaderLength;
+  for (BitmapGlyphBuilderList::iterator builder_map = glyph_builders_.begin(),
+                                        builder_end = glyph_builders_.end();
+                                        builder_map != builder_end;
+                                        builder_map++) {
+    for (BitmapGlyphBuilderMap::iterator glyph_entry = builder_map->begin(),
+                                         glyph_entry_end = builder_map->end();
+                                         glyph_entry != glyph_entry_end;
+                                         glyph_entry++) {
+      int32_t glyph_size = glyph_entry->second->SubDataSizeToSerialize();
+      size += abs(glyph_size);
+      fixed = (glyph_size <= 0) ? false : fixed;
+    }
+  }
+  return (fixed ? 1 : -1) * size;
+}
+
+bool EbdtTable::Builder::SubReadyToSerialize() {
+  if (glyph_builders_.empty()) {
+    return false;
+  }
+  return true;
+}
+
+int32_t EbdtTable::Builder::SubSerialize(WritableFontData* new_data) {
+  int32_t size = 0;
+  size += new_data->WriteFixed(Offset::kVersion, kVersion);
+  for (BitmapGlyphBuilderList::iterator builder_map = glyph_builders_.begin(),
+                                        builder_end = glyph_builders_.end();
+                                        builder_map != builder_end;
+                                        builder_map++) {
+    for (BitmapGlyphBuilderMap::iterator glyph_entry = builder_map->begin(),
+                                         glyph_entry_end = builder_map->end();
+                                         glyph_entry != glyph_entry_end;
+                                         glyph_entry++) {
+      WritableFontDataPtr slice;
+      slice.Attach(down_cast<WritableFontData*>(new_data->Slice(size)));
+      size += glyph_entry->second->SubSerialize(slice);
+    }
+  }
+  return size;
+}
+
+void EbdtTable::Builder::SetLoca(BitmapLocaList* loca_list) {
+  assert(loca_list);
+  Revert();
+  glyph_loca_.resize(loca_list->size());
+  std::copy(loca_list->begin(), loca_list->end(), glyph_loca_.begin());
+}
+
+void EbdtTable::Builder::GenerateLocaList(BitmapLocaList* output) {
+  assert(output);
+  output->clear();
+
+  if (glyph_builders_.empty()) {
+    if (glyph_loca_.empty()) {
+      return;
+    }
+  }
+
+  int start_offset = Offset::kHeaderLength;
+  for (BitmapGlyphBuilderList::iterator builder_map = glyph_builders_.begin(),
+                                        builder_end = glyph_builders_.end();
+                                        builder_map != builder_end;
+                                        builder_map++) {
+    BitmapGlyphInfoMap new_loca_map;
+    int32_t glyph_offset = 0;
+    for (BitmapGlyphBuilderMap::iterator glyph_entry = builder_map->begin(),
+                                         glyph_end = builder_map->end();
+                                         glyph_entry != glyph_end;
+                                         glyph_entry++) {
+      BitmapGlyphBuilderPtr builder = glyph_entry->second;
+      int32_t size = builder->SubDataSizeToSerialize();
+      BitmapGlyphInfoPtr info = new BitmapGlyphInfo(glyph_entry->first,
+          start_offset + glyph_offset, size, builder->format());
+      new_loca_map[glyph_entry->first] = info;
+      glyph_offset += size;
+    }
+    start_offset += glyph_offset;
+    output->push_back(new_loca_map);
+  }
+}
+
+BitmapGlyphBuilderList* EbdtTable::Builder::GlyphBuilders() {
+  return GetGlyphBuilders();
+}
+
+void EbdtTable::Builder::SetGlyphBuilders(
+    BitmapGlyphBuilderList* glyph_builders) {
+  glyph_builders_.clear();
+  std::copy(glyph_builders->begin(), glyph_builders->end(),
+            glyph_builders_.begin());
+  set_model_changed();
+}
+
+void EbdtTable::Builder::Revert() {
+  glyph_loca_.clear();
+  glyph_builders_.clear();
+  set_model_changed(false);
+}
+
+CALLER_ATTACH
+EbdtTable::Builder* EbdtTable::Builder::CreateBuilder(Header* header,
+                                                      WritableFontData* data) {
+  Ptr<EbdtTable::Builder> builder;
+  builder = new Builder(header, data);
+  return builder.Detach();
+}
+
+CALLER_ATTACH
+EbdtTable::Builder* EbdtTable::Builder::CreateBuilder(Header* header,
+                                                      ReadableFontData* data) {
+  Ptr<EbdtTable::Builder> builder;
+  builder = new Builder(header, data);
+  return builder.Detach();
+}
+
+BitmapGlyphBuilderList* EbdtTable::Builder::GetGlyphBuilders() {
+  if (glyph_builders_.empty()) {
+    if (glyph_loca_.empty()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IllegalStateException(
+          "Loca values not set - unable to parse glyph data.");
+#endif
+      return NULL;
+    }
+    Initialize(InternalReadData(), &glyph_loca_, &glyph_builders_);
+    set_model_changed();
+  }
+  return &glyph_builders_;
+}
+
+void EbdtTable::Builder::Initialize(ReadableFontData* data,
+                                    BitmapLocaList* loca_list,
+                                    BitmapGlyphBuilderList* output) {
+  assert(loca_list);
+  assert(output);
+
+  output->clear();
+  if (data) {
+    for (BitmapLocaList::iterator loca_map = loca_list->begin(),
+                                  loca_end = loca_list->end();
+                                  loca_map != loca_end; loca_map++) {
+      BitmapGlyphBuilderMap glyph_builder_map;
+      for (BitmapGlyphInfoMap::iterator entry = loca_map->begin(),
+                                        entry_end = loca_map->end();
+                                        entry != entry_end; entry++) {
+        BitmapGlyphInfoPtr info = entry->second;
+        ReadableFontDataPtr slice;
+        slice.Attach(down_cast<ReadableFontData*>(data->Slice(
+            info->offset(), info->length())));
+        BitmapGlyphBuilderPtr glyph_builder;
+        glyph_builder.Attach(BitmapGlyph::Builder::CreateGlyphBuilder(
+            slice, info->format()));
+        glyph_builder_map[entry->first] = glyph_builder;
+      }
+      output->push_back(glyph_builder_map);
+    }
+  }
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/ebdt_table.h b/sfntly/cpp/src/sfntly/table/bitmap/ebdt_table.h
new file mode 100644
index 0000000..d138c14
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/ebdt_table.h
@@ -0,0 +1,108 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBDT_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBDT_TABLE_H_
+
+#include "sfntly/table/bitmap/bitmap_glyph.h"
+#include "sfntly/table/bitmap/bitmap_glyph_info.h"
+#include "sfntly/table/subtable_container_table.h"
+
+namespace sfntly {
+
+class EbdtTable : public SubTableContainerTable,
+                  public RefCounted<EbdtTable> {
+ public:
+  struct Offset {
+    enum {
+      kVersion = 0,
+      kHeaderLength = DataSize::kFixed,
+    };
+  };
+
+  class Builder : public SubTableContainerTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual void SubDataSet();
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+    void SetLoca(BitmapLocaList* loca_list);
+    void GenerateLocaList(BitmapLocaList* output);
+
+    // Gets the List of glyph builders for the glyph table builder. These may be
+    // manipulated in any way by the caller and the changes will be reflected in
+    // the final glyph table produced.
+    // If there is no current data for the glyph builder or the glyph builders
+    // have not been previously set then this will return an empty glyph builder
+    // List. If there is current data (i.e. data read from an existing font) and
+    // the loca list has not been set or is null, empty, or invalid, then an
+    // empty glyph builder List will be returned.
+    // @return the list of glyph builders
+    BitmapGlyphBuilderList* GlyphBuilders();
+
+    // Replace the internal glyph builders with the one provided. The provided
+    // list and all contained objects belong to this builder.
+    // This call is only required if the entire set of glyphs in the glyph
+    // table builder are being replaced. If the glyph builder list provided from
+    // the {@link EbdtTable.Builder#glyphBuilders()} is being used and modified
+    // then those changes will already be reflected in the glyph table builder.
+    // @param glyphBuilders the new glyph builders
+    void SetGlyphBuilders(BitmapGlyphBuilderList* glyph_builders);
+
+    void Revert();
+
+    // Create a new builder using the header information and data provided.
+    // @param header the header information
+    // @param data the data holding the table
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                ReadableFontData* data);
+
+   private:
+    BitmapGlyphBuilderList* GetGlyphBuilders();
+    static void Initialize(ReadableFontData* data,
+                           BitmapLocaList* loca_list,
+                           BitmapGlyphBuilderList* output);
+
+    static const int32_t kVersion = 0x00020000;  // TODO(stuartg): const/enum
+    BitmapLocaList glyph_loca_;
+    BitmapGlyphBuilderList glyph_builders_;
+  };
+
+  virtual ~EbdtTable();
+  int32_t Version();
+  CALLER_ATTACH BitmapGlyph* Glyph(int32_t offset,
+                                   int32_t length,
+                                   int32_t format);
+ protected:
+  EbdtTable(Header* header, ReadableFontData* data);
+};
+typedef Ptr<EbdtTable> EbdtTablePtr;
+typedef Ptr<EbdtTable::Builder> EbdtTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBDT_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/eblc_table.cc b/sfntly/cpp/src/sfntly/table/bitmap/eblc_table.cc
new file mode 100644
index 0000000..0ad2764
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/eblc_table.cc
@@ -0,0 +1,313 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/eblc_table.h"
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include "sfntly/math/font_math.h"
+
+namespace sfntly {
+/******************************************************************************
+ * EblcTable class
+ ******************************************************************************/
+int32_t EblcTable::Version() {
+  return data_->ReadFixed(Offset::kVersion);
+}
+
+int32_t EblcTable::NumSizes() {
+  return data_->ReadULongAsInt(Offset::kNumSizes);
+}
+
+BitmapSizeTable* EblcTable::GetBitmapSizeTable(int32_t index) {
+  if (index < 0 || index > NumSizes()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException(
+        "Size table index is outside the range of tables.");
+#endif
+    return NULL;
+  }
+  BitmapSizeTableList* bitmap_size_table_list = GetBitmapSizeTableList();
+  if (bitmap_size_table_list) {
+    return (*bitmap_size_table_list)[index];
+  }
+  return NULL;
+}
+
+EblcTable::EblcTable(Header* header, ReadableFontData* data)
+    : SubTableContainerTable(header, data) {
+}
+
+BitmapSizeTableList* EblcTable::GetBitmapSizeTableList() {
+  AutoLock lock(bitmap_size_table_lock_);
+  if (bitmap_size_table_.empty()) {
+    CreateBitmapSizeTable(data_, NumSizes(), &bitmap_size_table_);
+  }
+  return &bitmap_size_table_;
+}
+
+// static
+void EblcTable::CreateBitmapSizeTable(ReadableFontData* data,
+                                      int32_t num_sizes,
+                                      BitmapSizeTableList* output) {
+  assert(data);
+  assert(output);
+  for (int32_t i = 0; i < num_sizes; ++i) {
+    ReadableFontDataPtr new_data;
+    new_data.Attach(down_cast<ReadableFontData*>(
+        data->Slice(Offset::kBitmapSizeTableArrayStart +
+                    i * Offset::kBitmapSizeTableLength,
+                    Offset::kBitmapSizeTableLength)));
+    BitmapSizeTableBuilderPtr size_builder;
+    size_builder.Attach(
+        BitmapSizeTable::Builder::CreateBuilder(new_data, data));
+    BitmapSizeTablePtr size;
+    size.Attach(down_cast<BitmapSizeTable*>(size_builder->Build()));
+    output->push_back(size);
+  }
+}
+
+/******************************************************************************
+ * EblcTable::Builder class
+ ******************************************************************************/
+EblcTable::Builder::Builder(Header* header, WritableFontData* data)
+    : SubTableContainerTable::Builder(header, data) {
+}
+
+EblcTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : SubTableContainerTable::Builder(header, data) {
+}
+
+EblcTable::Builder::~Builder() {
+}
+
+int32_t EblcTable::Builder::SubSerialize(WritableFontData* new_data) {
+  // header
+  int32_t size = new_data->WriteFixed(0, kVersion);
+  size += new_data->WriteULong(size, size_table_builders_.size());
+
+  // calculate the offsets
+  // offset to the start of the size table array
+  int32_t size_table_start_offset = size;
+  // walking offset in the size table array
+  int32_t size_table_offset = size_table_start_offset;
+  // offset to the start of the whole index subtable block
+  int32_t sub_table_block_start_offset = size_table_offset +
+      size_table_builders_.size() * Offset::kBitmapSizeTableLength;
+  // walking offset in the index subtable
+  // points to the start of the current subtable block
+  int32_t current_sub_table_block_start_offset = sub_table_block_start_offset;
+
+#if defined (SFNTLY_DEBUG_BITMAP)
+  int32_t size_index = 0;
+#endif
+  for (BitmapSizeTableBuilderList::iterator
+           size_builder = size_table_builders_.begin(),
+           size_builder_end = size_table_builders_.end();
+       size_builder != size_builder_end; size_builder++) {
+    (*size_builder)->SetIndexSubTableArrayOffset(
+        current_sub_table_block_start_offset);
+    IndexSubTableBuilderList* index_sub_table_builder_list =
+        (*size_builder)->IndexSubTableBuilders();
+
+    // walking offset within the current subTable array
+    int32_t index_sub_table_array_offset = current_sub_table_block_start_offset;
+    // walking offset within the subTable entries
+    int32_t index_sub_table_offset = index_sub_table_array_offset +
+        index_sub_table_builder_list->size() * Offset::kIndexSubHeaderLength;
+
+#if defined (SFNTLY_DEBUG_BITMAP)
+    fprintf(stderr, "size %d: sizeTable=%x, current subTable Block=%x, ",
+            size_index, size_table_offset,
+            current_sub_table_block_start_offset);
+    fprintf(stderr, "index subTableStart=%x\n", index_sub_table_offset);
+    size_index++;
+    int32_t sub_table_index = 0;
+#endif
+    for (IndexSubTableBuilderList::iterator
+             index_sub_table_builder = index_sub_table_builder_list->begin(),
+             index_sub_table_builder_end = index_sub_table_builder_list->end();
+         index_sub_table_builder != index_sub_table_builder_end;
+         index_sub_table_builder++) {
+#if defined (SFNTLY_DEBUG_BITMAP)
+      fprintf(stderr, "\tsubTableIndex %d: format=%x, ", sub_table_index,
+              (*index_sub_table_builder)->index_format());
+      fprintf(stderr, "indexSubTableArrayOffset=%x, indexSubTableOffset=%x\n",
+              index_sub_table_array_offset, index_sub_table_offset);
+      sub_table_index++;
+#endif
+      // array entry
+      index_sub_table_array_offset += new_data->WriteUShort(
+          index_sub_table_array_offset,
+          (*index_sub_table_builder)->first_glyph_index());
+      index_sub_table_array_offset += new_data->WriteUShort(
+          index_sub_table_array_offset,
+          (*index_sub_table_builder)->last_glyph_index());
+      index_sub_table_array_offset += new_data->WriteULong(
+          index_sub_table_array_offset,
+          index_sub_table_offset - current_sub_table_block_start_offset);
+
+      // index sub table
+      WritableFontDataPtr slice_index_sub_table;
+      slice_index_sub_table.Attach(down_cast<WritableFontData*>(
+          new_data->Slice(index_sub_table_offset)));
+      int32_t current_sub_table_size =
+          (*index_sub_table_builder)->SubSerialize(slice_index_sub_table);
+      int32_t padding = FontMath::PaddingRequired(current_sub_table_size,
+                                                  DataSize::kULONG);
+#if defined (SFNTLY_DEBUG_BITMAP)
+      fprintf(stderr, "\t\tsubTableSize = %x, padding = %x\n",
+              current_sub_table_size, padding);
+#endif
+      index_sub_table_offset += current_sub_table_size;
+      index_sub_table_offset +=
+          new_data->WritePadding(index_sub_table_offset, padding);
+    }
+
+    // serialize size table
+    (*size_builder)->SetIndexTableSize(
+        index_sub_table_offset - current_sub_table_block_start_offset);
+    WritableFontDataPtr slice_size_table;
+    slice_size_table.Attach(down_cast<WritableFontData*>(
+        new_data->Slice(size_table_offset)));
+    size_table_offset += (*size_builder)->SubSerialize(slice_size_table);
+
+    current_sub_table_block_start_offset = index_sub_table_offset;
+  }
+  return size + current_sub_table_block_start_offset;
+}
+
+bool EblcTable::Builder::SubReadyToSerialize() {
+  if (size_table_builders_.empty()) {
+    return false;
+  }
+  for (BitmapSizeTableBuilderList::iterator b = size_table_builders_.begin(),
+                                            e = size_table_builders_.end();
+                                            b != e; b++) {
+    if (!(*b)->SubReadyToSerialize()) {
+      return false;
+    }
+  }
+  return true;
+}
+
+int32_t EblcTable::Builder::SubDataSizeToSerialize() {
+  if (size_table_builders_.empty()) {
+    return 0;
+  }
+  int32_t size = Offset::kHeaderLength;
+  bool variable = false;
+#if defined (SFNTLY_DEBUG_BITMAP)
+  size_t size_index = 0;
+#endif
+  for (BitmapSizeTableBuilderList::iterator b = size_table_builders_.begin(),
+                                            e = size_table_builders_.end();
+                                            b != e; b++) {
+    int32_t size_builder_size = (*b)->SubDataSizeToSerialize();
+#if defined (SFNTLY_DEBUG_BITMAP)
+    fprintf(stderr, "sizeIndex = %d, sizeBuilderSize=0x%x (%d)\n",
+            size_index++, size_builder_size, size_builder_size);
+#endif
+    variable = size_builder_size > 0 ? variable : true;
+    size += abs(size_builder_size);
+  }
+#if defined (SFNTLY_DEBUG_BITMAP)
+  fprintf(stderr, "eblc size=%d\n", size);
+#endif
+  return variable ? -size : size;
+}
+
+void EblcTable::Builder::SubDataSet() {
+  Revert();
+}
+
+BitmapSizeTableBuilderList* EblcTable::Builder::BitmapSizeBuilders() {
+  return GetSizeList();
+}
+
+void EblcTable::Builder::Revert() {
+  size_table_builders_.clear();
+  set_model_changed(false);
+}
+
+void EblcTable::Builder::GenerateLocaList(BitmapLocaList* output) {
+  assert(output);
+  BitmapSizeTableBuilderList* size_builder_list = GetSizeList();
+  output->clear();
+#if defined (SFNTLY_DEBUG_BITMAP)
+  int32_t size_index = 0;
+#endif
+  for (BitmapSizeTableBuilderList::iterator b = size_builder_list->begin(),
+                                            e = size_builder_list->end();
+                                            b != e; b++) {
+#if defined (SFNTLY_DEBUG_BITMAP)
+    fprintf(stderr, "size table = %d\n", size_index++);
+#endif
+    BitmapGlyphInfoMap loca_map;
+    (*b)->GenerateLocaMap(&loca_map);
+    output->push_back(loca_map);
+  }
+}
+
+CALLER_ATTACH
+FontDataTable* EblcTable::Builder::SubBuildTable(ReadableFontData* data) {
+  Ptr<EblcTable> new_table = new EblcTable(header(), data);
+  return new_table.Detach();
+}
+
+// static
+CALLER_ATTACH EblcTable::Builder*
+    EblcTable::Builder::CreateBuilder(Header* header, WritableFontData* data) {
+  Ptr<EblcTable::Builder> new_builder = new EblcTable::Builder(header, data);
+  return new_builder.Detach();
+}
+
+// static
+CALLER_ATTACH EblcTable::Builder*
+    EblcTable::Builder::CreateBuilder(Header* header, ReadableFontData* data) {
+  Ptr<EblcTable::Builder> new_builder = new EblcTable::Builder(header, data);
+  return new_builder.Detach();
+}
+
+BitmapSizeTableBuilderList* EblcTable::Builder::GetSizeList() {
+  if (size_table_builders_.empty()) {
+    Initialize(InternalReadData(), &size_table_builders_);
+    set_model_changed();
+  }
+  return &size_table_builders_;
+}
+
+void EblcTable::Builder::Initialize(ReadableFontData* data,
+                                    BitmapSizeTableBuilderList* output) {
+  assert(output);
+  if (data) {
+    int32_t num_sizes = data->ReadULongAsInt(Offset::kNumSizes);
+    for (int32_t i = 0; i < num_sizes; ++i) {
+      ReadableFontDataPtr new_data;
+      new_data.Attach(down_cast<ReadableFontData*>(
+          data->Slice(Offset::kBitmapSizeTableArrayStart +
+                      i * Offset::kBitmapSizeTableLength,
+                      Offset::kBitmapSizeTableLength)));
+      BitmapSizeTableBuilderPtr size_builder;
+      size_builder.Attach(BitmapSizeTable::Builder::CreateBuilder(
+          new_data, data));
+      output->push_back(size_builder);
+    }
+  }
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/eblc_table.h b/sfntly/cpp/src/sfntly/table/bitmap/eblc_table.h
new file mode 100644
index 0000000..b04338a
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/eblc_table.h
@@ -0,0 +1,194 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBLC_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBLC_TABLE_H_
+
+#include "sfntly/port/lock.h"
+#include "sfntly/table/bitmap/big_glyph_metrics.h"
+#include "sfntly/table/bitmap/bitmap_glyph.h"
+#include "sfntly/table/bitmap/bitmap_size_table.h"
+#include "sfntly/table/subtable_container_table.h"
+
+namespace sfntly {
+
+class EblcTable : public SubTableContainerTable,
+                  public RefCounted<EblcTable> {
+ public:
+  struct Offset {
+    enum {
+      // header
+      kVersion = 0,
+      kNumSizes = 4,
+      kHeaderLength = kNumSizes + DataSize::kULONG,
+
+      // bitmapSizeTable
+      kBitmapSizeTableArrayStart = kHeaderLength,
+      kBitmapSizeTableLength = 48,
+      kBitmapSizeTable_indexSubTableArrayOffset = 0,
+      kBitmapSizeTable_indexTableSize = 4,
+      kBitmapSizeTable_numberOfIndexSubTables = 8,
+      kBitmapSizeTable_colorRef = 12,
+      kBitmapSizeTable_hori = 16,
+      kBitmapSizeTable_vert = 28,
+      kBitmapSizeTable_startGlyphIndex = 40,
+      kBitmapSizeTable_endGlyphIndex = 42,
+      kBitmapSizeTable_ppemX = 44,
+      kBitmapSizeTable_ppemY = 45,
+      kBitmapSizeTable_bitDepth = 46,
+      kBitmapSizeTable_flags = 47,
+
+      // sbitLineMetrics
+      kSbitLineMetricsLength = 12,
+      kSbitLineMetrics_ascender = 0,
+      kSbitLineMetrics_descender = 1,
+      kSbitLineMetrics_widthMax = 2,
+      kSbitLineMetrics_caretSlopeNumerator = 3,
+      kSbitLineMetrics_caretSlopeDenominator = 4,
+      kSbitLineMetrics_caretOffset = 5,
+      kSbitLineMetrics_minOriginSB = 6,
+      kSbitLineMetrics_minAdvanceSB = 7,
+      kSbitLineMetrics_maxBeforeBL = 8,
+      kSbitLineMetrics_minAfterBL = 9,
+      kSbitLineMetrics_pad1 = 10,
+      kSbitLineMetrics_pad2 = 11,
+
+      // indexSubTable
+      kIndexSubTableEntryLength = 8,
+      kIndexSubTableEntry_firstGlyphIndex = 0,
+      kIndexSubTableEntry_lastGlyphIndex = 2,
+      kIndexSubTableEntry_additionalOffsetToIndexSubTable = 4,
+
+      // indexSubHeader
+      kIndexSubHeaderLength = 8,
+      kIndexSubHeader_indexFormat = 0,
+      kIndexSubHeader_imageFormat = 2,
+      kIndexSubHeader_imageDataOffset = 4,
+
+      // indexSubTable - all offset relative to the subtable start
+
+      // indexSubTable1
+      kIndexSubTable1_offsetArray = kIndexSubHeaderLength,
+      kIndexSubTable1_builderDataSize = kIndexSubHeaderLength,
+
+      // kIndexSubTable2
+      kIndexSubTable2Length = kIndexSubHeaderLength +
+                              DataSize::kULONG +
+                              BitmapGlyph::Offset::kBigGlyphMetricsLength,
+      kIndexSubTable2_imageSize = kIndexSubHeaderLength,
+      kIndexSubTable2_bigGlyphMetrics = kIndexSubTable2_imageSize +
+                                        DataSize::kULONG,
+      kIndexSubTable2_builderDataSize = kIndexSubTable2_bigGlyphMetrics +
+                                        BigGlyphMetrics::Offset::kMetricsLength,
+
+      // kIndexSubTable3
+      kIndexSubTable3_offsetArray = kIndexSubHeaderLength,
+      kIndexSubTable3_builderDataSize = kIndexSubTable3_offsetArray,
+
+      // kIndexSubTable4
+      kIndexSubTable4_numGlyphs = kIndexSubHeaderLength,
+      kIndexSubTable4_glyphArray = kIndexSubTable4_numGlyphs +
+                                   DataSize::kULONG,
+      kIndexSubTable4_codeOffsetPairLength = 2 * DataSize::kUSHORT,
+      kIndexSubTable4_codeOffsetPair_glyphCode = 0,
+      kIndexSubTable4_codeOffsetPair_offset = DataSize::kUSHORT,
+      kIndexSubTable4_builderDataSize = kIndexSubTable4_glyphArray,
+
+      // kIndexSubTable5
+      kIndexSubTable5_imageSize = kIndexSubHeaderLength,
+      kIndexSubTable5_bigGlyphMetrics = kIndexSubTable5_imageSize +
+                                        DataSize::kULONG,
+      kIndexSubTable5_numGlyphs = kIndexSubTable5_bigGlyphMetrics +
+                                  BitmapGlyph::Offset::kBigGlyphMetricsLength,
+      kIndexSubTable5_glyphArray = kIndexSubTable5_numGlyphs +
+                                   DataSize::kULONG,
+      kIndexSubTable5_builderDataSize = kIndexSubTable5_glyphArray,
+
+      // codeOffsetPair
+      kCodeOffsetPairLength = 2 * DataSize::kUSHORT,
+      kCodeOffsetPair_glyphCode = 0,
+      kCodeOffsetPair_offset = DataSize::kUSHORT,
+    };
+  };
+
+  class Builder : public SubTableContainerTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual void SubDataSet();
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+    BitmapSizeTableBuilderList* BitmapSizeBuilders();
+    void Revert();
+
+    // Generates the loca list for the EBDT table. The list is intended to be
+    // used by the EBDT to allow it to parse the glyph data and generate glyph
+    // objects. After returning from this method the list belongs to the caller.
+    // The list entries are in the same order as the size table builders are at
+    // the time of this call.
+    // @return the list of loca maps with one for each size table builder
+    void GenerateLocaList(BitmapLocaList* output);
+
+    // Create a new builder using the header information and data provided.
+    // @param header the header information
+    // @param data the data holding the table
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                ReadableFontData* data);
+
+   private:
+    BitmapSizeTableBuilderList* GetSizeList();
+    void Initialize(ReadableFontData* data, BitmapSizeTableBuilderList* output);
+
+    static const int32_t kVersion = 0x00020000;
+    BitmapSizeTableBuilderList size_table_builders_;
+  };
+
+  int32_t Version();
+  int32_t NumSizes();
+  // UNIMPLEMENTED: toString()
+
+  BitmapSizeTable* GetBitmapSizeTable(int32_t index);
+
+  static const int32_t NOTDEF = -1;
+
+ protected:
+  EblcTable(Header* header, ReadableFontData* data);
+
+ private:
+  BitmapSizeTableList* GetBitmapSizeTableList();
+
+  static void CreateBitmapSizeTable(ReadableFontData* data,
+                                    int32_t num_sizes,
+                                    BitmapSizeTableList* output);
+
+  Lock bitmap_size_table_lock_;
+  BitmapSizeTableList bitmap_size_table_;
+};
+typedef Ptr<EblcTable> EblcTablePtr;
+typedef Ptr<EblcTable::Builder> EblcTableBuilderPtr;
+}
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBLC_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/ebsc_table.cc b/sfntly/cpp/src/sfntly/table/bitmap/ebsc_table.cc
new file mode 100644
index 0000000..458c2d4
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/ebsc_table.cc
@@ -0,0 +1,107 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/ebsc_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * EbscTable class
+ ******************************************************************************/
+EbscTable::~EbscTable() {
+}
+
+int32_t EbscTable::Version() {
+  return data_->ReadFixed(Offset::kVersion);
+}
+
+int32_t EbscTable::NumSizes() {
+  return data_->ReadULongAsInt(Offset::kNumSizes);
+}
+
+EbscTable::EbscTable(Header* header, ReadableFontData* data)
+    : Table(header, data) {
+}
+
+/******************************************************************************
+ * EbscTable::BitmapScaleTable class
+ ******************************************************************************/
+EbscTable::BitmapScaleTable::~BitmapScaleTable() {
+}
+
+EbscTable::BitmapScaleTable::BitmapScaleTable(ReadableFontData* data)
+    : SubTable(data) {
+}
+
+int32_t EbscTable::BitmapScaleTable::PpemX() {
+  return data_->ReadByte(Offset::kBitmapScaleTable_ppemX);
+}
+
+int32_t EbscTable::BitmapScaleTable::PpemY() {
+  return data_->ReadByte(Offset::kBitmapScaleTable_ppemY);
+}
+
+int32_t EbscTable::BitmapScaleTable::SubstitutePpemX() {
+  return data_->ReadByte(Offset::kBitmapScaleTable_substitutePpemX);
+}
+
+int32_t EbscTable::BitmapScaleTable::SubstitutePpemY() {
+  return data_->ReadByte(Offset::kBitmapScaleTable_substitutePpemY);
+}
+
+/******************************************************************************
+ * EbscTable::Builder class
+ ******************************************************************************/
+EbscTable::Builder::~Builder() {
+}
+
+CALLER_ATTACH EbscTable::Builder* EbscTable::Builder::CreateBuilder(
+    Header* header, WritableFontData* data) {
+  EbscTableBuilderPtr builder = new EbscTable::Builder(header, data);
+  return builder.Detach();
+}
+
+EbscTable::Builder::Builder(Header* header, WritableFontData* data)
+    : Table::Builder(header, data) {
+}
+
+EbscTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : Table::Builder(header, data) {
+}
+
+CALLER_ATTACH
+FontDataTable* EbscTable::Builder::SubBuildTable(ReadableFontData* data) {
+  EbscTablePtr output = new EbscTable(header(), data);
+  return output.Detach();
+}
+
+void EbscTable::Builder::SubDataSet() {
+  // NOP
+}
+
+int32_t EbscTable::Builder::SubDataSizeToSerialize() {
+  return 0;
+}
+
+bool EbscTable::Builder::SubReadyToSerialize() {
+  return false;
+}
+
+int32_t EbscTable::Builder::SubSerialize(WritableFontData* new_data) {
+  UNREFERENCED_PARAMETER(new_data);
+  return 0;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/ebsc_table.h b/sfntly/cpp/src/sfntly/table/bitmap/ebsc_table.h
new file mode 100644
index 0000000..b79df38
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/ebsc_table.h
@@ -0,0 +1,101 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBSC_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBSC_TABLE_H_
+
+#include "sfntly/table/bitmap/eblc_table.h"
+
+namespace sfntly {
+
+class EbscTable : public Table,
+                  public RefCounted<EbscTable> {
+ public:
+  struct Offset {
+    enum {
+      // header
+      kVersion = 0,
+      kNumSizes = DataSize::kFixed,
+      kHeaderLength = kNumSizes + DataSize::kULONG,
+      kBitmapScaleTableStart = kHeaderLength,
+
+      // bitmapScaleTable
+      kBitmapScaleTable_hori = 0,
+      kBitmapScaleTable_vert = EblcTable::Offset::kSbitLineMetricsLength,
+      kBitmapScaleTable_ppemX = kBitmapScaleTable_vert +
+                                EblcTable::Offset::kSbitLineMetricsLength,
+      kBitmapScaleTable_ppemY = kBitmapScaleTable_ppemX + DataSize::kBYTE,
+      kBitmapScaleTable_substitutePpemX = kBitmapScaleTable_ppemY +
+                                          DataSize::kBYTE,
+      kBitmapScaleTable_substitutePpemY = kBitmapScaleTable_substitutePpemX +
+                                          DataSize::kBYTE,
+      kBitmapScaleTableLength = kBitmapScaleTable_substitutePpemY +
+                                DataSize::kBYTE,
+    };
+  };
+
+  class BitmapScaleTable : public SubTable,
+                           public RefCounted<BitmapScaleTable> {
+   public:
+    virtual ~BitmapScaleTable();
+    int32_t PpemX();
+    int32_t PpemY();
+    int32_t SubstitutePpemX();
+    int32_t SubstitutePpemY();
+
+   protected:
+    // Note: caller to do data->Slice(offset, Offset::kBitmapScaleTableLength)
+    explicit BitmapScaleTable(ReadableFontData* data);
+  };
+
+  // TODO(stuartg): currently the builder just builds from initial data
+  // - need to make fully working but few if any examples to test with
+  class Builder : public Table::Builder,
+                  public RefCounted<Builder> {
+   public:
+    virtual ~Builder();
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+   protected:
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+  };
+
+  virtual ~EbscTable();
+
+  int32_t Version();
+  int32_t NumSizes();
+  // Note: renamed from bitmapScaleTable
+  CALLER_ATTACH BitmapScaleTable* GetBitmapScaleTable(int32_t index);
+
+ private:
+  EbscTable(Header* header, ReadableFontData* data);
+  friend class Builder;
+};
+typedef Ptr<EbscTable> EbscTablePtr;
+typedef Ptr<EbscTable::Builder> EbscTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_EBSC_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/glyph_metrics.cc b/sfntly/cpp/src/sfntly/table/bitmap/glyph_metrics.cc
new file mode 100644
index 0000000..e91eb99
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/glyph_metrics.cc
@@ -0,0 +1,39 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/glyph_metrics.h"
+
+namespace sfntly {
+
+GlyphMetrics::~GlyphMetrics() {
+}
+
+GlyphMetrics::GlyphMetrics(ReadableFontData* data)
+    : SubTable(data) {
+}
+
+GlyphMetrics::Builder::~Builder() {
+}
+
+GlyphMetrics::Builder::Builder(WritableFontData* data)
+    : SubTable::Builder(data) {
+}
+
+GlyphMetrics::Builder::Builder(ReadableFontData* data)
+    : SubTable::Builder(data) {
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/glyph_metrics.h b/sfntly/cpp/src/sfntly/table/bitmap/glyph_metrics.h
new file mode 100644
index 0000000..5f16aaa
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/glyph_metrics.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_GLYPH_METRICS_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_GLYPH_METRICS_H_
+
+#include "sfntly/table/subtable.h"
+
+namespace sfntly {
+
+class GlyphMetrics : public SubTable {
+ public:
+  virtual ~GlyphMetrics();
+
+ protected:
+  class Builder : public SubTable::Builder {
+   public:
+    virtual ~Builder();
+
+   protected:
+    explicit Builder(WritableFontData* data);
+    explicit Builder(ReadableFontData* data);
+  };
+
+  explicit GlyphMetrics(ReadableFontData* data);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_GLYPH_METRICS_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table.cc b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table.cc
new file mode 100644
index 0000000..5e29784
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table.cc
@@ -0,0 +1,278 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/index_sub_table.h"
+
+#include "sfntly/table/bitmap/eblc_table.h"
+#include "sfntly/table/bitmap/index_sub_table_format1.h"
+#include "sfntly/table/bitmap/index_sub_table_format2.h"
+#include "sfntly/table/bitmap/index_sub_table_format3.h"
+#include "sfntly/table/bitmap/index_sub_table_format4.h"
+#include "sfntly/table/bitmap/index_sub_table_format5.h"
+
+namespace sfntly {
+/******************************************************************************
+ * IndexSubTable class
+ ******************************************************************************/
+CALLER_ATTACH BitmapGlyphInfo* IndexSubTable::GlyphInfo(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return NULL;
+  }
+  if (GlyphStartOffset(glyph_id) == -1) {
+    return NULL;
+  }
+  BitmapGlyphInfoPtr output = new BitmapGlyphInfo(glyph_id,
+                                                  image_data_offset(),
+                                                  GlyphStartOffset(glyph_id),
+                                                  GlyphLength(glyph_id),
+                                                  image_format());
+  return output.Detach();
+}
+
+int32_t IndexSubTable::GlyphOffset(int32_t glyph_id) {
+  int32_t glyph_start_offset = GlyphStartOffset(glyph_id);
+  if (glyph_start_offset == -1) {
+    return -1;
+  }
+  return image_data_offset() + glyph_start_offset;
+}
+
+// static
+CALLER_ATTACH IndexSubTable*
+    IndexSubTable::CreateIndexSubTable(ReadableFontData* data,
+                                       int32_t offset_to_index_sub_table_array,
+                                       int32_t array_index) {
+  IndexSubTableBuilderPtr builder;
+  builder.Attach(IndexSubTable::Builder::CreateBuilder(
+      data, offset_to_index_sub_table_array, array_index));
+  return down_cast<IndexSubTable*>(builder->Build());
+}
+
+IndexSubTable::IndexSubTable(ReadableFontData* data,
+                             int32_t first_glyph_index,
+                             int32_t last_glyph_index)
+    : SubTable(data),
+      first_glyph_index_(first_glyph_index),
+      last_glyph_index_(last_glyph_index) {
+  index_format_ =
+      data_->ReadUShort(EblcTable::Offset::kIndexSubHeader_indexFormat);
+  image_format_ =
+      data_->ReadUShort(EblcTable::Offset::kIndexSubHeader_imageFormat);
+  image_data_offset_ =
+      data_->ReadULongAsInt(EblcTable::Offset::kIndexSubHeader_imageDataOffset);
+}
+
+int32_t IndexSubTable::CheckGlyphRange(int32_t glyph_id) {
+  return CheckGlyphRange(glyph_id, first_glyph_index(), last_glyph_index());
+}
+
+// static
+int32_t IndexSubTable::CheckGlyphRange(int32_t glyph_id,
+                                       int32_t first_glyph_id,
+                                       int32_t last_glyph_id) {
+  if (glyph_id < first_glyph_id || glyph_id > last_glyph_id) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException("Glyph ID is outside of the allowed range.");
+#endif
+    return -1;
+  }
+  return glyph_id - first_glyph_id;
+}
+
+/******************************************************************************
+ * IndexSubTable::Builder class
+ ******************************************************************************/
+IndexSubTable::Builder::~Builder() {
+}
+
+void IndexSubTable::Builder::Revert() {
+  set_model_changed(false);
+  Initialize(InternalReadData());
+}
+
+CALLER_ATTACH BitmapGlyphInfo* IndexSubTable::Builder::GlyphInfo(
+    int32_t glyph_id) {
+  BitmapGlyphInfoPtr glyph_info =
+      new BitmapGlyphInfo(glyph_id,
+                          image_data_offset(),
+                          GlyphStartOffset(glyph_id),
+                          GlyphLength(glyph_id),
+                          image_format());
+  return glyph_info.Detach();
+}
+
+int32_t IndexSubTable::Builder::GlyphOffset(int32_t glyph_id) {
+  return image_data_offset() + GlyphStartOffset(glyph_id);
+}
+
+// static
+CALLER_ATTACH IndexSubTable::Builder*
+IndexSubTable::Builder::CreateBuilder(int32_t index_format) {
+  switch (index_format) {
+    case Format::FORMAT_1:
+      return IndexSubTableFormat1::Builder::CreateBuilder();
+    case Format::FORMAT_2:
+      return IndexSubTableFormat2::Builder::CreateBuilder();
+    case Format::FORMAT_3:
+      return IndexSubTableFormat3::Builder::CreateBuilder();
+    case Format::FORMAT_4:
+      return IndexSubTableFormat4::Builder::CreateBuilder();
+    case Format::FORMAT_5:
+      return IndexSubTableFormat5::Builder::CreateBuilder();
+    default:
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IllegalArgumentException("Invalid index subtable format");
+#endif
+      return NULL;
+  }
+}
+
+// static
+CALLER_ATTACH IndexSubTable::Builder*
+IndexSubTable::Builder::CreateBuilder(ReadableFontData* data,
+    int32_t offset_to_index_sub_table_array, int32_t array_index) {
+  int32_t index_sub_table_entry_offset =
+      offset_to_index_sub_table_array +
+      array_index * EblcTable::Offset::kIndexSubTableEntryLength;
+  int32_t first_glyph_index =
+      data->ReadUShort(index_sub_table_entry_offset +
+                       EblcTable::Offset::kIndexSubTableEntry_firstGlyphIndex);
+  int32_t last_glyph_index =
+      data->ReadUShort(index_sub_table_entry_offset +
+                       EblcTable::Offset::kIndexSubTableEntry_lastGlyphIndex);
+  int32_t additional_offset_to_index_subtable = data->ReadULongAsInt(
+      index_sub_table_entry_offset +
+      EblcTable::Offset::kIndexSubTableEntry_additionalOffsetToIndexSubTable);
+  int32_t index_sub_table_offset = offset_to_index_sub_table_array +
+                                   additional_offset_to_index_subtable;
+  int32_t index_format = data->ReadUShort(index_sub_table_offset);
+  switch (index_format) {
+    case 1:
+      return IndexSubTableFormat1::Builder::CreateBuilder(
+          data, index_sub_table_offset, first_glyph_index, last_glyph_index);
+    case 2:
+      return IndexSubTableFormat2::Builder::CreateBuilder(
+          data, index_sub_table_offset, first_glyph_index, last_glyph_index);
+    case 3:
+      return IndexSubTableFormat3::Builder::CreateBuilder(
+          data, index_sub_table_offset, first_glyph_index, last_glyph_index);
+    case 4:
+      return IndexSubTableFormat4::Builder::CreateBuilder(
+          data, index_sub_table_offset, first_glyph_index, last_glyph_index);
+    case 5:
+      return IndexSubTableFormat5::Builder::CreateBuilder(
+          data, index_sub_table_offset, first_glyph_index, last_glyph_index);
+    default:
+      // Unknown format and unable to process.
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IllegalArgumentException("Invalid Index Subtable Format");
+#endif
+      break;
+  }
+  return NULL;
+}
+
+CALLER_ATTACH
+FontDataTable* IndexSubTable::Builder::SubBuildTable(ReadableFontData* data) {
+  UNREFERENCED_PARAMETER(data);
+  return NULL;
+}
+
+void IndexSubTable::Builder::SubDataSet() {
+  // NOP
+}
+
+int32_t IndexSubTable::Builder::SubDataSizeToSerialize() {
+  return 0;
+}
+
+bool IndexSubTable::Builder::SubReadyToSerialize() {
+  return false;
+}
+
+int32_t IndexSubTable::Builder::SubSerialize(WritableFontData* new_data) {
+  UNREFERENCED_PARAMETER(new_data);
+  return 0;
+}
+
+IndexSubTable::Builder::Builder(int32_t data_size, int32_t index_format)
+    : SubTable::Builder(data_size),
+      first_glyph_index_(0),
+      last_glyph_index_(0),
+      index_format_(index_format),
+      image_format_(0),
+      image_data_offset_(0) {
+}
+
+IndexSubTable::Builder::Builder(int32_t index_format,
+                                int32_t image_format,
+                                int32_t image_data_offset,
+                                int32_t data_size)
+    : SubTable::Builder(data_size),
+      first_glyph_index_(0),
+      last_glyph_index_(0),
+      index_format_(index_format),
+      image_format_(image_format),
+      image_data_offset_(image_data_offset) {
+}
+
+IndexSubTable::Builder::Builder(WritableFontData* data,
+                                int32_t first_glyph_index,
+                                int32_t last_glyph_index)
+    : SubTable::Builder(data),
+      first_glyph_index_(first_glyph_index),
+      last_glyph_index_(last_glyph_index) {
+  Initialize(data);
+}
+
+IndexSubTable::Builder::Builder(ReadableFontData* data,
+                                int32_t first_glyph_index,
+                                int32_t last_glyph_index)
+    : SubTable::Builder(data),
+      first_glyph_index_(first_glyph_index),
+      last_glyph_index_(last_glyph_index) {
+  Initialize(data);
+}
+
+int32_t IndexSubTable::Builder::CheckGlyphRange(int32_t glyph_id) {
+  return IndexSubTable::CheckGlyphRange(glyph_id,
+                                        first_glyph_index(),
+                                        last_glyph_index());
+}
+
+int32_t IndexSubTable::Builder::SerializeIndexSubHeader(
+    WritableFontData* data) {
+  int32_t size =
+      data->WriteUShort(EblcTable::Offset::kIndexSubHeader_indexFormat,
+                        index_format());
+  size += data->WriteUShort(EblcTable::Offset::kIndexSubHeader_imageFormat,
+                            image_format());
+  size += data->WriteULong(EblcTable::Offset::kIndexSubHeader_imageDataOffset,
+                           image_data_offset());
+  return size;
+}
+
+void IndexSubTable::Builder::Initialize(ReadableFontData* data) {
+  index_format_ =
+      data->ReadUShort(EblcTable::Offset::kIndexSubHeader_indexFormat);
+  image_format_ =
+      data->ReadUShort(EblcTable::Offset::kIndexSubHeader_imageFormat);
+  image_data_offset_ =
+      data->ReadULongAsInt(EblcTable::Offset::kIndexSubHeader_imageDataOffset);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table.h b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table.h
new file mode 100644
index 0000000..6d27129
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table.h
@@ -0,0 +1,178 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_H_
+
+#include <vector>
+
+#include "sfntly/port/java_iterator.h"
+#include "sfntly/table/subtable.h"
+#include "sfntly/table/bitmap/bitmap_glyph_info.h"
+
+namespace sfntly {
+
+class IndexSubTable : public SubTable {
+ public:
+  struct Format {
+    enum {
+      FORMAT_1 = 1,
+      FORMAT_2 = 2,
+      FORMAT_3 = 3,
+      FORMAT_4 = 4,
+      FORMAT_5 = 5,
+    };
+  };
+
+  class Builder : public SubTable::Builder {
+   public:
+    virtual ~Builder();
+
+    void Revert();
+
+    int32_t index_format() { return index_format_; }
+    int32_t first_glyph_index() { return first_glyph_index_; }
+    void set_first_glyph_index(int32_t v) { first_glyph_index_ = v; }
+    int32_t last_glyph_index() { return last_glyph_index_; }
+    void set_last_glyph_index(int32_t v) { last_glyph_index_ = v; }
+    int32_t image_format() { return image_format_; }
+    void set_image_format(int32_t v) { image_format_ = v; }
+    int32_t image_data_offset() { return image_data_offset_; }
+    void set_image_data_offset(int32_t v) { image_data_offset_ = v; }
+
+    virtual int32_t NumGlyphs() = 0;
+
+    // Gets the glyph info for the specified glyph id.
+    // @param glyphId the glyph id to look up
+    // @return the glyph info
+    CALLER_ATTACH virtual BitmapGlyphInfo* GlyphInfo(int32_t glyph_id);
+
+    // Gets the full offset of the glyph within the EBDT table.
+    // @param glyphId the glyph id
+    // @return the glyph offset
+    virtual int32_t GlyphOffset(int32_t glyph_id);
+
+    // Gets the offset of the glyph relative to the block for this index
+    // subtable.
+    // @param glyphId the glyph id
+    // @return the glyph offset
+    virtual int32_t GlyphStartOffset(int32_t glyph_id) = 0;
+
+    // Gets the length of the glyph within the EBDT table.
+    // @param glyphId the glyph id
+    // @return the glyph offset
+    virtual int32_t GlyphLength(int32_t glyph_id) = 0;
+
+    // Note: renamed from java iterator()
+    CALLER_ATTACH virtual Iterator<BitmapGlyphInfo, IndexSubTable::Builder>*
+        GetIterator() = 0;
+
+    // Static instantiation function.
+    static CALLER_ATTACH Builder* CreateBuilder(int32_t index_format);
+    static CALLER_ATTACH Builder*
+        CreateBuilder(ReadableFontData* data,
+                      int32_t offset_to_index_sub_table_array,
+                      int32_t array_index);
+
+    // The following methods will never be called but they need to be here to
+    // allow the BitmapSizeTable to see these methods through an abstract
+    // reference.
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+   protected:
+    Builder(int32_t data_size, int32_t index_format);
+    Builder(int32_t index_format,
+            int32_t image_format,
+            int32_t image_data_offset,
+            int32_t data_size);
+    Builder(WritableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    Builder(ReadableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+
+    // Checks that the glyph id is within the correct range. If it returns the
+    // offset of the glyph id from the start of the range.
+    // @param glyphId
+    // @return the offset of the glyphId from the start of the glyph range
+    // @throws IndexOutOfBoundsException if the glyph id is not within the
+    //         correct range
+    int32_t CheckGlyphRange(int32_t glyph_id);
+    int32_t SerializeIndexSubHeader(WritableFontData* data);
+
+   private:
+    void Initialize(ReadableFontData* data);
+
+    int32_t first_glyph_index_;
+    int32_t last_glyph_index_;
+    int32_t index_format_;
+    int32_t image_format_;
+    int32_t image_data_offset_;
+  };
+
+  int32_t index_format() { return index_format_; }
+  int32_t first_glyph_index() { return first_glyph_index_; }
+  int32_t last_glyph_index() { return last_glyph_index_; }
+  int32_t image_format() { return image_format_; }
+  int32_t image_data_offset() { return image_data_offset_; }
+
+  CALLER_ATTACH BitmapGlyphInfo* GlyphInfo(int32_t glyph_id);
+  virtual int32_t GlyphOffset(int32_t glyph_id);
+  virtual int32_t GlyphStartOffset(int32_t glyph_id) = 0;
+  virtual int32_t GlyphLength(int32_t glyph_id) = 0;
+  virtual int32_t NumGlyphs() = 0;
+
+  static CALLER_ATTACH IndexSubTable*
+      CreateIndexSubTable(ReadableFontData* data,
+                          int32_t offset_to_index_sub_table_array,
+                          int32_t array_index);
+
+ protected:
+  // Note: the constructor does not implement offset/length form provided in
+  //       Java to avoid heavy lifting in constructors.  Callers to call
+  //       GetDataLength() static method of the derived class to get proper
+  //       length and slice ahead.
+  IndexSubTable(ReadableFontData* data,
+                int32_t first_glyph_index,
+                int32_t last_glyph_index);
+
+  int32_t CheckGlyphRange(int32_t glyph_id);
+  static int32_t CheckGlyphRange(int32_t glyph_id,
+                                 int32_t first_glyph_id,
+                                 int32_t last_glyph_id);
+
+ private:
+  int32_t first_glyph_index_;
+  int32_t last_glyph_index_;
+  int32_t index_format_;
+  int32_t image_format_;
+  int32_t image_data_offset_;
+};
+typedef Ptr<IndexSubTable> IndexSubTablePtr;
+typedef std::vector<IndexSubTablePtr> IndexSubTableList;
+typedef Ptr<IndexSubTable::Builder> IndexSubTableBuilderPtr;
+typedef std::vector<IndexSubTableBuilderPtr> IndexSubTableBuilderList;
+typedef Iterator<BitmapGlyphInfo, IndexSubTable::Builder> BitmapGlyphInfoIter;
+typedef Ptr<BitmapGlyphInfoIter> BitmapGlyphInfoIterPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format1.cc b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format1.cc
new file mode 100644
index 0000000..5199e18
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format1.cc
@@ -0,0 +1,302 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/index_sub_table_format1.h"
+
+#include "sfntly/table/bitmap/eblc_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * IndexSubTableFormat1 class
+ ******************************************************************************/
+// static
+int32_t IndexSubTableFormat1::GetDataLength(ReadableFontData* data,
+                                            int32_t offset,
+                                            int32_t first,
+                                            int32_t last) {
+  UNREFERENCED_PARAMETER(data);
+  UNREFERENCED_PARAMETER(offset);
+  return (last - first + 1 + 1) * DataSize::kULONG;
+}
+
+IndexSubTableFormat1::~IndexSubTableFormat1() {
+}
+
+int32_t IndexSubTableFormat1::NumGlyphs() {
+  return last_glyph_index() - first_glyph_index() + 1;
+}
+
+int32_t IndexSubTableFormat1::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  return Loca(loca);
+}
+
+int32_t IndexSubTableFormat1::GlyphLength(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  return Loca(loca + 1) - Loca(loca);
+}
+
+IndexSubTableFormat1::IndexSubTableFormat1(ReadableFontData* data,
+                                           int32_t first_glyph_index,
+                                           int32_t last_glyph_index)
+    : IndexSubTable(data, first_glyph_index, last_glyph_index) {
+}
+
+int32_t IndexSubTableFormat1::Loca(int32_t loca) {
+  return image_data_offset() +
+         data_->ReadULongAsInt(EblcTable::Offset::kIndexSubTable1_offsetArray +
+                               loca * DataSize::kULONG);
+}
+
+/******************************************************************************
+ * IndexSubTableFormat1::Builder class
+ ******************************************************************************/
+IndexSubTableFormat1::Builder::~Builder() {
+}
+
+int32_t IndexSubTableFormat1::Builder::NumGlyphs() {
+  return GetOffsetArray()->size() - 1;
+}
+
+int32_t IndexSubTableFormat1::Builder::GlyphLength(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return 0;
+  }
+  IntegerList* offset_array = GetOffsetArray();
+  return offset_array->at(loca + 1) - offset_array->at(loca);
+}
+
+int32_t IndexSubTableFormat1::Builder::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  return GetOffsetArray()->at(loca);
+}
+
+CALLER_ATTACH IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator*
+    IndexSubTableFormat1::Builder::GetIterator() {
+  Ptr<IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator> it =
+      new IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator(this);
+  return it.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat1::Builder*
+IndexSubTableFormat1::Builder::CreateBuilder() {
+  IndexSubTableFormat1BuilderPtr output = new IndexSubTableFormat1::Builder();
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat1::Builder*
+IndexSubTableFormat1::Builder::CreateBuilder(ReadableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  ReadableFontDataPtr new_data;
+  new_data.Attach(down_cast<ReadableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  if (new_data == NULL) {
+    return NULL;
+  }
+  IndexSubTableFormat1BuilderPtr output =
+      new IndexSubTableFormat1::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+
+// static
+CALLER_ATTACH IndexSubTableFormat1::Builder*
+IndexSubTableFormat1::Builder::CreateBuilder(WritableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  WritableFontDataPtr new_data;
+  new_data.Attach(down_cast<WritableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  IndexSubTableFormat1BuilderPtr output =
+      new IndexSubTableFormat1::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+CALLER_ATTACH FontDataTable* IndexSubTableFormat1::Builder::SubBuildTable(
+    ReadableFontData* data) {
+  IndexSubTableFormat1Ptr output = new IndexSubTableFormat1(
+      data, first_glyph_index(), last_glyph_index());
+  return output.Detach();
+}
+
+void IndexSubTableFormat1::Builder::SubDataSet() {
+  Revert();
+}
+
+int32_t IndexSubTableFormat1::Builder::SubDataSizeToSerialize() {
+  if (offset_array_.empty()) {
+    return InternalReadData()->Length();
+  }
+  return EblcTable::Offset::kIndexSubHeaderLength +
+         offset_array_.size() * DataSize::kULONG;
+}
+
+bool IndexSubTableFormat1::Builder::SubReadyToSerialize() {
+  if (!offset_array_.empty()) {
+    return true;
+  }
+  return false;
+}
+
+int32_t IndexSubTableFormat1::Builder::SubSerialize(
+    WritableFontData* new_data) {
+  int32_t size = SerializeIndexSubHeader(new_data);
+  if (!model_changed()) {
+    if (InternalReadData() == NULL) {
+      return size;
+    }
+    ReadableFontDataPtr source;
+    WritableFontDataPtr target;
+    source.Attach(down_cast<ReadableFontData*>(InternalReadData()->Slice(
+        EblcTable::Offset::kIndexSubTable1_offsetArray)));
+    target.Attach(down_cast<WritableFontData*>(new_data->Slice(
+        EblcTable::Offset::kIndexSubTable1_offsetArray)));
+    size += source->CopyTo(target);
+  } else {
+    for (IntegerList::iterator b = GetOffsetArray()->begin(),
+                               e = GetOffsetArray()->end(); b != e; b++) {
+      size += new_data->WriteLong(size, *b);
+    }
+  }
+  return size;
+}
+
+IntegerList* IndexSubTableFormat1::Builder::OffsetArray() {
+  return GetOffsetArray();
+}
+
+void IndexSubTableFormat1::Builder::SetOffsetArray(
+    const IntegerList& offset_array) {
+  offset_array_.clear();
+  offset_array_ = offset_array;
+  set_model_changed();
+}
+
+void IndexSubTableFormat1::Builder::Revert() {
+  offset_array_.clear();
+  IndexSubTable::Builder::Revert();
+}
+
+IndexSubTableFormat1::Builder::Builder()
+    : IndexSubTable::Builder(EblcTable::Offset::kIndexSubTable1_builderDataSize,
+                             IndexSubTable::Format::FORMAT_1) {
+}
+
+IndexSubTableFormat1::Builder::Builder(WritableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IndexSubTableFormat1::Builder::Builder(ReadableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IntegerList* IndexSubTableFormat1::Builder::GetOffsetArray() {
+  if (offset_array_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &offset_array_;
+}
+
+void IndexSubTableFormat1::Builder::Initialize(ReadableFontData* data) {
+  offset_array_.clear();
+  if (data) {
+    int32_t num_offsets = (last_glyph_index() - first_glyph_index() + 1) + 1;
+    for (int32_t i = 0; i < num_offsets; ++i) {
+      offset_array_.push_back(data->ReadULongAsInt(
+          EblcTable::Offset::kIndexSubTable1_offsetArray +
+          i * DataSize::kULONG));
+    }
+  }
+}
+
+// static
+int32_t IndexSubTableFormat1::Builder::DataLength(
+    ReadableFontData* data,
+    int32_t index_sub_table_offset,
+    int32_t first_glyph_index,
+    int32_t last_glyph_index) {
+  UNREFERENCED_PARAMETER(data);
+  UNREFERENCED_PARAMETER(index_sub_table_offset);
+  return EblcTable::Offset::kIndexSubHeaderLength +
+         (last_glyph_index - first_glyph_index + 1 + 1) * DataSize::kULONG;
+}
+
+/******************************************************************************
+ * IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator class
+ ******************************************************************************/
+IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator::BitmapGlyphInfoIterator(
+    IndexSubTableFormat1::Builder* container)
+    : RefIterator<BitmapGlyphInfo, IndexSubTableFormat1::Builder,
+                  IndexSubTable::Builder>(container) {
+  glyph_id_ = container->first_glyph_index();
+}
+
+bool IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator::HasNext() {
+  if (glyph_id_ <= container()->last_glyph_index()) {
+    return true;
+  }
+  return false;
+}
+
+CALLER_ATTACH BitmapGlyphInfo*
+IndexSubTableFormat1::Builder::BitmapGlyphInfoIterator::Next() {
+  BitmapGlyphInfoPtr output;
+  if (!HasNext()) {
+    // Note: In C++, we do not throw exception when there's no element.
+    return NULL;
+  }
+  output = new BitmapGlyphInfo(glyph_id_,
+                               container()->image_data_offset(),
+                               container()->GlyphStartOffset(glyph_id_),
+                               container()->GlyphLength(glyph_id_),
+                               container()->image_format());
+  glyph_id_++;
+  return output.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format1.h b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format1.h
new file mode 100644
index 0000000..33171c1
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format1.h
@@ -0,0 +1,116 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT1_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT1_H_
+
+#include "sfntly/port/java_iterator.h"
+#include "sfntly/table/bitmap/index_sub_table.h"
+
+namespace sfntly {
+// Format 1 Index Subtable Entry.
+class IndexSubTableFormat1 : public IndexSubTable,
+                             public RefCounted<IndexSubTableFormat1> {
+ public:
+  class Builder : public IndexSubTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    class BitmapGlyphInfoIterator
+        : public RefIterator<BitmapGlyphInfo, Builder, IndexSubTable::Builder> {
+     public:
+      explicit BitmapGlyphInfoIterator(Builder* container);
+      virtual ~BitmapGlyphInfoIterator() {}
+
+      virtual bool HasNext();
+      CALLER_ATTACH virtual BitmapGlyphInfo* Next();
+
+     private:
+      int32_t glyph_id_;
+    };
+
+    virtual ~Builder();
+    virtual int32_t NumGlyphs();
+    virtual int32_t GlyphLength(int32_t glyph_id);
+    virtual int32_t GlyphStartOffset(int32_t glyph_id);
+    CALLER_ATTACH virtual BitmapGlyphInfoIterator* GetIterator();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    IntegerList* OffsetArray();
+    void SetOffsetArray(const IntegerList& offset_array);
+    CALLER_ATTACH BitmapGlyphInfoIter* Iterator();
+
+    static CALLER_ATTACH Builder* CreateBuilder();
+    static CALLER_ATTACH Builder* CreateBuilder(ReadableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+    static CALLER_ATTACH Builder* CreateBuilder(WritableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+
+   protected:
+    void Revert();
+
+   private:
+    Builder();
+    Builder(WritableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    Builder(ReadableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    IntegerList* GetOffsetArray();
+    void Initialize(ReadableFontData* data);
+
+    static int32_t DataLength(ReadableFontData* data,
+                              int32_t index_sub_table_offset,
+                              int32_t first_glyph_index,
+                              int32_t last_glyph_index);
+
+    IntegerList offset_array_;
+  };
+
+  virtual ~IndexSubTableFormat1();
+
+  virtual int32_t NumGlyphs();
+  virtual int32_t GlyphStartOffset(int32_t glyph_id);
+  virtual int32_t GlyphLength(int32_t glyph_id);
+
+  static int32_t GetDataLength(ReadableFontData* data,
+                               int32_t offset,
+                               int32_t first,
+                               int32_t last);
+
+ private:
+  IndexSubTableFormat1(ReadableFontData* data,
+                       int32_t first_glyph_index,
+                       int32_t last_glyph_index);
+  int32_t Loca(int32_t loca_index);
+
+  friend class Builder;
+};
+typedef Ptr<IndexSubTableFormat1> IndexSubTableFormat1Ptr;
+typedef Ptr<IndexSubTableFormat1::Builder> IndexSubTableFormat1BuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT1_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format2.cc b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format2.cc
new file mode 100644
index 0000000..ce73e9b
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format2.cc
@@ -0,0 +1,275 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/index_sub_table_format2.h"
+
+#include "sfntly/table/bitmap/eblc_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * IndexSubTableFormat2 class
+ ******************************************************************************/
+IndexSubTableFormat2::~IndexSubTableFormat2() {
+}
+
+int32_t IndexSubTableFormat2::ImageSize() {
+  return data_->ReadULongAsInt(EblcTable::Offset::kIndexSubTable2_imageSize);
+}
+
+CALLER_ATTACH BigGlyphMetrics* IndexSubTableFormat2::BigMetrics() {
+  ReadableFontDataPtr slice;
+  slice.Attach(down_cast<ReadableFontData*>(
+      data_->Slice(EblcTable::Offset::kIndexSubTable2_bigGlyphMetrics,
+                   BigGlyphMetrics::Offset::kMetricsLength)));
+  BigGlyphMetricsPtr output = new BigGlyphMetrics(slice);
+  return output.Detach();
+}
+
+int32_t IndexSubTableFormat2::NumGlyphs() {
+  return last_glyph_index() - first_glyph_index() + 1;
+}
+
+int32_t IndexSubTableFormat2::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  return loca * image_size_;
+}
+
+int32_t IndexSubTableFormat2::GlyphLength(int32_t glyph_id) {
+  if (CheckGlyphRange(glyph_id) == -1) {
+    return 0;
+  }
+  return image_size_;
+}
+
+IndexSubTableFormat2::IndexSubTableFormat2(ReadableFontData* data,
+                                           int32_t first,
+                                           int32_t last)
+    : IndexSubTable(data, first, last) {
+  image_size_ =
+      data_->ReadULongAsInt(EblcTable::Offset::kIndexSubTable2_imageSize);
+}
+
+/******************************************************************************
+ * IndexSubTableFormat2::Builder class
+ ******************************************************************************/
+IndexSubTableFormat2::Builder::~Builder() {
+}
+
+int32_t IndexSubTableFormat2::Builder::NumGlyphs() {
+  return last_glyph_index() - first_glyph_index() + 1;
+}
+
+int32_t IndexSubTableFormat2::Builder::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  return loca * ImageSize();
+}
+
+int32_t IndexSubTableFormat2::Builder::GlyphLength(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return 0;
+  }
+  return ImageSize();
+}
+
+CALLER_ATTACH IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator*
+    IndexSubTableFormat2::Builder::GetIterator() {
+  Ptr<IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator> it =
+      new IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator(this);
+  return it.Detach();
+}
+
+int32_t IndexSubTableFormat2::Builder::ImageSize() {
+  return InternalReadData()->ReadULongAsInt(
+      EblcTable::Offset::kIndexSubTable2_imageSize);
+}
+
+void IndexSubTableFormat2::Builder::SetImageSize(int32_t image_size) {
+  InternalWriteData()->WriteULong(EblcTable::Offset::kIndexSubTable2_imageSize,
+                                  image_size);
+}
+
+BigGlyphMetrics::Builder* IndexSubTableFormat2::Builder::BigMetrics() {
+  if (metrics_ == NULL) {
+    WritableFontDataPtr data;
+    data.Attach(down_cast<WritableFontData*>(InternalWriteData()->Slice(
+        EblcTable::Offset::kIndexSubTable2_bigGlyphMetrics,
+        BigGlyphMetrics::Offset::kMetricsLength)));
+    metrics_ = new BigGlyphMetrics::Builder(data);
+  }
+  return metrics_;
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat2::Builder*
+IndexSubTableFormat2::Builder::CreateBuilder() {
+  IndexSubTableFormat2BuilderPtr output = new IndexSubTableFormat2::Builder();
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat2::Builder*
+IndexSubTableFormat2::Builder::CreateBuilder(ReadableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  ReadableFontDataPtr new_data;
+  new_data.Attach(down_cast<ReadableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  if (new_data == NULL) {
+    return NULL;
+  }
+  IndexSubTableFormat2BuilderPtr output =
+      new IndexSubTableFormat2::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat2::Builder*
+IndexSubTableFormat2::Builder::CreateBuilder(WritableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  WritableFontDataPtr new_data;
+  new_data.Attach(down_cast<WritableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  IndexSubTableFormat2BuilderPtr output =
+      new IndexSubTableFormat2::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+CALLER_ATTACH FontDataTable* IndexSubTableFormat2::Builder::SubBuildTable(
+    ReadableFontData* data) {
+  IndexSubTableFormat2Ptr output = new IndexSubTableFormat2(
+      data, first_glyph_index(), last_glyph_index());
+  return output.Detach();
+}
+
+void IndexSubTableFormat2::Builder::SubDataSet() {
+  Revert();
+}
+
+int32_t IndexSubTableFormat2::Builder::SubDataSizeToSerialize() {
+  return EblcTable::Offset::kIndexSubTable2Length;
+}
+
+bool IndexSubTableFormat2::Builder::SubReadyToSerialize() {
+  return true;
+}
+
+int32_t IndexSubTableFormat2::Builder::SubSerialize(
+    WritableFontData* new_data) {
+  int32_t size = SerializeIndexSubHeader(new_data);
+  if (metrics_ == NULL) {
+    ReadableFontDataPtr source;
+    WritableFontDataPtr target;
+    source.Attach(down_cast<ReadableFontData*>(
+        InternalReadData()->Slice(size)));
+    target.Attach(down_cast<WritableFontData*>(new_data->Slice(size)));
+    size += source->CopyTo(target);
+  } else {
+    WritableFontDataPtr slice;
+    size += new_data->WriteLong(EblcTable::Offset::kIndexSubTable2_imageSize,
+                                ImageSize());
+    slice.Attach(down_cast<WritableFontData*>(new_data->Slice(size)));
+    size += metrics_->SubSerialize(slice);
+  }
+  return size;
+}
+
+IndexSubTableFormat2::Builder::Builder()
+    : IndexSubTable::Builder(EblcTable::Offset::kIndexSubTable3_builderDataSize,
+                             IndexSubTable::Format::FORMAT_2) {
+  metrics_.Attach(BigGlyphMetrics::Builder::CreateBuilder());
+}
+
+IndexSubTableFormat2::Builder::Builder(WritableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IndexSubTableFormat2::Builder::Builder(ReadableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+// static
+int32_t IndexSubTableFormat2::Builder::DataLength(
+    ReadableFontData* data,
+    int32_t index_sub_table_offset,
+    int32_t first_glyph_index,
+    int32_t last_glyph_index) {
+  UNREFERENCED_PARAMETER(data);
+  UNREFERENCED_PARAMETER(index_sub_table_offset);
+  UNREFERENCED_PARAMETER(first_glyph_index);
+  UNREFERENCED_PARAMETER(last_glyph_index);
+  return EblcTable::Offset::kIndexSubTable2Length;
+}
+
+/******************************************************************************
+ * IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator class
+ ******************************************************************************/
+IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator::BitmapGlyphInfoIterator(
+    IndexSubTableFormat2::Builder* container)
+    : RefIterator<BitmapGlyphInfo, IndexSubTableFormat2::Builder,
+                  IndexSubTable::Builder>(container) {
+  glyph_id_ = container->first_glyph_index();
+}
+
+bool IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator::HasNext() {
+  if (glyph_id_ <= container()->last_glyph_index()) {
+    return true;
+  }
+  return false;
+}
+
+CALLER_ATTACH BitmapGlyphInfo*
+IndexSubTableFormat2::Builder::BitmapGlyphInfoIterator::Next() {
+  BitmapGlyphInfoPtr output;
+  if (!HasNext()) {
+    // Note: In C++, we do not throw exception when there's no element.
+    return NULL;
+  }
+  output = new BitmapGlyphInfo(glyph_id_,
+                               container()->image_data_offset(),
+                               container()->GlyphStartOffset(glyph_id_),
+                               container()->GlyphLength(glyph_id_),
+                               container()->image_format());
+  glyph_id_++;
+  return output.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format2.h b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format2.h
new file mode 100644
index 0000000..784e8a3
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format2.h
@@ -0,0 +1,106 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT2_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT2_H_
+
+#include "sfntly/table/bitmap/index_sub_table.h"
+#include "sfntly/table/bitmap/big_glyph_metrics.h"
+
+namespace sfntly {
+// Format 2 Index Subtable Entry.
+class IndexSubTableFormat2 : public IndexSubTable,
+                             public RefCounted<IndexSubTableFormat2> {
+ public:
+  class Builder : public IndexSubTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    class BitmapGlyphInfoIterator
+        : public RefIterator<BitmapGlyphInfo, Builder, IndexSubTable::Builder> {
+     public:
+      explicit BitmapGlyphInfoIterator(Builder* container);
+      virtual ~BitmapGlyphInfoIterator() {}
+
+      virtual bool HasNext();
+      CALLER_ATTACH virtual BitmapGlyphInfo* Next();
+
+     private:
+      int32_t glyph_id_;
+    };
+
+    virtual ~Builder();
+    virtual int32_t NumGlyphs();
+    virtual int32_t GlyphStartOffset(int32_t glyph_id);
+    virtual int32_t GlyphLength(int32_t glyph_id);
+    CALLER_ATTACH virtual BitmapGlyphInfoIterator* GetIterator();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    int32_t ImageSize();
+    void SetImageSize(int32_t image_size);
+    BigGlyphMetrics::Builder* BigMetrics();
+
+    static CALLER_ATTACH Builder* CreateBuilder();
+    static CALLER_ATTACH Builder* CreateBuilder(ReadableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+    static CALLER_ATTACH Builder* CreateBuilder(WritableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+   private:
+    Builder();
+    Builder(WritableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    Builder(ReadableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+
+    static int32_t DataLength(ReadableFontData* data,
+                              int32_t index_sub_table_offset,
+                              int32_t first_glyph_index,
+                              int32_t last_glyph_index);
+
+    BigGlyphMetricsBuilderPtr metrics_;
+  };
+
+  virtual ~IndexSubTableFormat2();
+
+  int32_t ImageSize();
+  CALLER_ATTACH BigGlyphMetrics* BigMetrics();
+
+  virtual int32_t NumGlyphs();
+  virtual int32_t GlyphStartOffset(int32_t glyph_id);
+  virtual int32_t GlyphLength(int32_t glyph_id);
+
+ private:
+  IndexSubTableFormat2(ReadableFontData* data, int32_t first, int32_t last);
+
+  int32_t image_size_;
+  friend class Builder;
+};
+typedef Ptr<IndexSubTableFormat2> IndexSubTableFormat2Ptr;
+typedef Ptr<IndexSubTableFormat2::Builder> IndexSubTableFormat2BuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT1_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format3.cc b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format3.cc
new file mode 100644
index 0000000..e2679b7
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format3.cc
@@ -0,0 +1,298 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/index_sub_table_format3.h"
+
+#include "sfntly/table/bitmap/eblc_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * IndexSubTableFormat3 class
+ ******************************************************************************/
+IndexSubTableFormat3::~IndexSubTableFormat3() {
+}
+
+int32_t IndexSubTableFormat3::NumGlyphs() {
+  return last_glyph_index() - first_glyph_index() + 1;
+}
+
+int32_t IndexSubTableFormat3::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca != -1) {
+    return Loca(loca);
+  }
+  return -1;
+}
+
+int32_t IndexSubTableFormat3::GlyphLength(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca != -1) {
+    return Loca(glyph_id + 1) - Loca(glyph_id);
+  }
+  return 0;
+}
+
+// static
+int32_t IndexSubTableFormat3::GetDataLength(ReadableFontData* data,
+                                            int32_t offset,
+                                            int32_t first,
+                                            int32_t last) {
+  UNREFERENCED_PARAMETER(data);
+  UNREFERENCED_PARAMETER(offset);
+  return (last - first + 1 + 1) * DataSize::kUSHORT;
+}
+
+IndexSubTableFormat3::IndexSubTableFormat3(ReadableFontData* data,
+                                           int32_t first_glyph_index,
+                                           int32_t last_glyph_index)
+    : IndexSubTable(data, first_glyph_index, last_glyph_index) {
+}
+
+int32_t IndexSubTableFormat3::Loca(int32_t loca) {
+  int32_t read_offset =
+      data_->ReadUShort(EblcTable::Offset::kIndexSubTable3_offsetArray +
+                        loca * DataSize::kUSHORT);
+  return read_offset;
+}
+
+/******************************************************************************
+ * IndexSubTableFormat3::Builder class
+ ******************************************************************************/
+IndexSubTableFormat3::Builder::~Builder() {
+}
+
+int32_t IndexSubTableFormat3::Builder::NumGlyphs() {
+  return GetOffsetArray()->size() - 1;
+}
+
+int32_t IndexSubTableFormat3::Builder::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  return GetOffsetArray()->at(loca);
+}
+
+int32_t IndexSubTableFormat3::Builder::GlyphLength(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return 0;
+  }
+  IntegerList* offset_array = GetOffsetArray();
+  return offset_array->at(loca + 1) - offset_array->at(loca);
+}
+
+CALLER_ATTACH IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator*
+    IndexSubTableFormat3::Builder::GetIterator() {
+  Ptr<IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator> it =
+      new IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator(this);
+  return it.Detach();
+}
+
+void IndexSubTableFormat3::Builder::Revert() {
+  offset_array_.clear();
+  IndexSubTable::Builder::Revert();
+}
+
+void IndexSubTableFormat3::Builder::SetOffsetArray(
+    const IntegerList& offset_array) {
+  offset_array_.clear();
+  offset_array_ = offset_array;
+  set_model_changed();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat3::Builder*
+IndexSubTableFormat3::Builder::CreateBuilder() {
+  IndexSubTableFormat3BuilderPtr output = new IndexSubTableFormat3::Builder();
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat3::Builder*
+IndexSubTableFormat3::Builder::CreateBuilder(ReadableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  ReadableFontDataPtr new_data;
+  new_data.Attach(down_cast<ReadableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  if (new_data == NULL) {
+    return NULL;
+  }
+  IndexSubTableFormat3BuilderPtr output =
+      new IndexSubTableFormat3::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat3::Builder*
+IndexSubTableFormat3::Builder::CreateBuilder(WritableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  WritableFontDataPtr new_data;
+  new_data.Attach(down_cast<WritableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  IndexSubTableFormat3BuilderPtr output =
+      new IndexSubTableFormat3::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+CALLER_ATTACH FontDataTable* IndexSubTableFormat3::Builder::SubBuildTable(
+    ReadableFontData* data) {
+  IndexSubTableFormat3Ptr output = new IndexSubTableFormat3(
+      data, first_glyph_index(), last_glyph_index());
+  return output.Detach();
+}
+
+void IndexSubTableFormat3::Builder::SubDataSet() {
+  Revert();
+}
+
+int32_t IndexSubTableFormat3::Builder::SubDataSizeToSerialize() {
+  if (offset_array_.empty()) {
+    return InternalReadData()->Length();
+  }
+  return EblcTable::Offset::kIndexSubHeaderLength +
+         offset_array_.size() * DataSize::kULONG;
+}
+
+bool IndexSubTableFormat3::Builder::SubReadyToSerialize() {
+  if (!offset_array_.empty()) {
+    return true;
+  }
+  return false;
+}
+
+int32_t IndexSubTableFormat3::Builder::SubSerialize(
+    WritableFontData* new_data) {
+  int32_t size = SerializeIndexSubHeader(new_data);
+  if (!model_changed()) {
+    if (InternalReadData() == NULL) {
+      return size;
+    }
+    ReadableFontDataPtr source;
+    WritableFontDataPtr target;
+    source.Attach(down_cast<ReadableFontData*>(InternalReadData()->Slice(
+        EblcTable::Offset::kIndexSubTable3_offsetArray)));
+    target.Attach(down_cast<WritableFontData*>(new_data->Slice(
+        EblcTable::Offset::kIndexSubTable3_offsetArray)));
+    size += source->CopyTo(target);
+  } else {
+    for (IntegerList::iterator b = GetOffsetArray()->begin(),
+                               e = GetOffsetArray()->end(); b != e; b++) {
+      size += new_data->WriteUShort(size, *b);
+    }
+  }
+  return size;
+}
+
+IndexSubTableFormat3::Builder::Builder()
+    : IndexSubTable::Builder(EblcTable::Offset::kIndexSubTable3_builderDataSize,
+                             IndexSubTable::Format::FORMAT_3) {
+}
+
+IndexSubTableFormat3::Builder::Builder(WritableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IndexSubTableFormat3::Builder::Builder(ReadableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IntegerList* IndexSubTableFormat3::Builder::GetOffsetArray() {
+  if (offset_array_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &offset_array_;
+}
+
+void IndexSubTableFormat3::Builder::Initialize(ReadableFontData* data) {
+  offset_array_.clear();
+  if (data) {
+    int32_t num_offsets = (last_glyph_index() - first_glyph_index() + 1) + 1;
+    for (int32_t i = 0; i < num_offsets; ++i) {
+      offset_array_.push_back(data->ReadUShort(
+         EblcTable::Offset::kIndexSubTable3_offsetArray +
+         i * DataSize::kUSHORT));
+    }
+  }
+}
+
+// static
+int32_t IndexSubTableFormat3::Builder::DataLength(
+    ReadableFontData* data,
+    int32_t index_sub_table_offset,
+    int32_t first_glyph_index,
+    int32_t last_glyph_index) {
+  UNREFERENCED_PARAMETER(data);
+  UNREFERENCED_PARAMETER(index_sub_table_offset);
+  return EblcTable::Offset::kIndexSubHeaderLength +
+         (last_glyph_index - first_glyph_index + 1 + 1) * DataSize::kUSHORT;
+}
+
+/******************************************************************************
+ * IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator class
+ ******************************************************************************/
+IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator::BitmapGlyphInfoIterator(
+    IndexSubTableFormat3::Builder* container)
+    : RefIterator<BitmapGlyphInfo, IndexSubTableFormat3::Builder,
+                  IndexSubTable::Builder>(container) {
+  glyph_id_ = container->first_glyph_index();
+}
+
+bool IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator::HasNext() {
+  if (glyph_id_ <= container()->last_glyph_index()) {
+    return true;
+  }
+  return false;
+}
+
+CALLER_ATTACH BitmapGlyphInfo*
+IndexSubTableFormat3::Builder::BitmapGlyphInfoIterator::Next() {
+  BitmapGlyphInfoPtr output;
+  if (!HasNext()) {
+    // Note: In C++, we do not throw exception when there's no element.
+    return NULL;
+  }
+  output = new BitmapGlyphInfo(glyph_id_,
+                               container()->image_data_offset(),
+                               container()->GlyphStartOffset(glyph_id_),
+                               container()->GlyphLength(glyph_id_),
+                               container()->image_format());
+  glyph_id_++;
+  return output.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format3.h b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format3.h
new file mode 100644
index 0000000..d71f857
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format3.h
@@ -0,0 +1,113 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT3_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT3_H_
+
+#include "sfntly/table/bitmap/index_sub_table.h"
+
+namespace sfntly {
+// Format 3 Index Subtable Entry.
+class IndexSubTableFormat3 : public IndexSubTable,
+                             public RefCounted<IndexSubTableFormat3> {
+ public:
+  class Builder : public IndexSubTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    class BitmapGlyphInfoIterator
+        : public RefIterator<BitmapGlyphInfo, Builder, IndexSubTable::Builder> {
+     public:
+      explicit BitmapGlyphInfoIterator(Builder* container);
+      virtual ~BitmapGlyphInfoIterator() {}
+
+      virtual bool HasNext();
+      CALLER_ATTACH virtual BitmapGlyphInfo* Next();
+
+     private:
+      int32_t glyph_id_;
+    };
+
+    virtual ~Builder();
+    virtual int32_t NumGlyphs();
+    virtual int32_t GlyphStartOffset(int32_t glyph_id);
+    virtual int32_t GlyphLength(int32_t glyph_id);
+    CALLER_ATTACH virtual BitmapGlyphInfoIterator* GetIterator();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    void SetOffsetArray(const IntegerList& offset_array);
+
+    static CALLER_ATTACH Builder* CreateBuilder();
+    static CALLER_ATTACH Builder* CreateBuilder(ReadableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+    static CALLER_ATTACH Builder* CreateBuilder(WritableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+
+   protected:
+    void Revert();
+
+   private:
+    Builder();
+    Builder(WritableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    Builder(ReadableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    IntegerList* GetOffsetArray();
+    void Initialize(ReadableFontData* data);
+
+    static int32_t DataLength(ReadableFontData* data,
+                              int32_t index_sub_table_offset,
+                              int32_t first_glyph_index,
+                              int32_t last_glyph_index);
+
+    IntegerList offset_array_;
+  };
+
+  virtual ~IndexSubTableFormat3();
+
+  virtual int32_t NumGlyphs();
+  virtual int32_t GlyphStartOffset(int32_t glyph_id);
+  virtual int32_t GlyphLength(int32_t glyph_id);
+
+  static int32_t GetDataLength(ReadableFontData* data,
+                               int32_t offset,
+                               int32_t first,
+                               int32_t last);
+
+ private:
+  IndexSubTableFormat3(ReadableFontData* data,
+                       int32_t first_glyph_index,
+                       int32_t last_glyph_index);
+  int32_t Loca(int32_t loca_index);
+
+  friend class Builder;
+};
+typedef Ptr<IndexSubTableFormat3> IndexSubTableFormat3Ptr;
+typedef Ptr<IndexSubTableFormat3::Builder> IndexSubTableFormat3BuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT3_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format4.cc b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format4.cc
new file mode 100644
index 0000000..5baa2a5
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format4.cc
@@ -0,0 +1,384 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/index_sub_table_format4.h"
+
+#include "sfntly/table/bitmap/eblc_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * IndexSubTableFormat4 class
+ ******************************************************************************/
+IndexSubTableFormat4::~IndexSubTableFormat4() {
+}
+
+int32_t IndexSubTableFormat4::NumGlyphs() {
+  return IndexSubTableFormat4::NumGlyphs(data_, 0);
+}
+
+int32_t IndexSubTableFormat4::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  int32_t pair_index = FindCodeOffsetPair(glyph_id);
+  if (pair_index < 0) {
+    return -1;
+  }
+  return data_->ReadUShort(EblcTable::Offset::kIndexSubTable4_glyphArray +
+                           pair_index *
+                           EblcTable::Offset::kCodeOffsetPairLength +
+                           EblcTable::Offset::kCodeOffsetPair_offset);
+}
+
+int32_t IndexSubTableFormat4::GlyphLength(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+
+  int32_t pair_index = FindCodeOffsetPair(glyph_id);
+  if (pair_index < 0) {
+    return -1;
+  }
+  return data_->ReadUShort(
+             EblcTable::Offset::kIndexSubTable4_glyphArray +
+             (pair_index + 1) * EblcTable::Offset::kCodeOffsetPairLength +
+             EblcTable::Offset::kCodeOffsetPair_offset) -
+         data_->ReadUShort(
+             EblcTable::Offset::kIndexSubTable4_glyphArray +
+             (pair_index) * EblcTable::Offset::kCodeOffsetPairLength +
+             EblcTable::Offset::kCodeOffsetPair_offset);
+}
+
+IndexSubTableFormat4::IndexSubTableFormat4(ReadableFontData* data,
+                                           int32_t first,
+                                           int32_t last)
+    : IndexSubTable(data, first, last) {
+}
+
+int32_t IndexSubTableFormat4::FindCodeOffsetPair(int32_t glyph_id) {
+  return data_->SearchUShort(EblcTable::Offset::kIndexSubTable4_glyphArray,
+                             EblcTable::Offset::kCodeOffsetPairLength,
+                             NumGlyphs(),
+                             glyph_id);
+}
+
+int32_t IndexSubTableFormat4::NumGlyphs(ReadableFontData* data,
+                                        int32_t table_offset) {
+  int32_t num_glyphs = data->ReadULongAsInt(table_offset +
+      EblcTable::Offset::kIndexSubTable4_numGlyphs);
+  return num_glyphs;
+}
+
+/******************************************************************************
+ * IndexSubTableFormat4::CodeOffsetPair related class
+ ******************************************************************************/
+IndexSubTableFormat4::CodeOffsetPair::CodeOffsetPair(int32_t glyph_code,
+                                                     int32_t offset)
+    : glyph_code_(glyph_code), offset_(offset) {
+}
+
+IndexSubTableFormat4::CodeOffsetPairBuilder::CodeOffsetPairBuilder()
+    : CodeOffsetPair(0, 0) {
+}
+
+IndexSubTableFormat4::CodeOffsetPairBuilder::CodeOffsetPairBuilder(
+    int32_t glyph_code, int32_t offset)
+    : CodeOffsetPair(glyph_code, offset) {
+}
+
+bool IndexSubTableFormat4::CodeOffsetPairGlyphCodeComparator::operator()(
+    const CodeOffsetPair& lhs, const CodeOffsetPair& rhs) {
+  return lhs.glyph_code() < rhs.glyph_code();
+}
+
+/******************************************************************************
+ * IndexSubTableFormat4::Builder class
+ ******************************************************************************/
+IndexSubTableFormat4::Builder::~Builder() {
+}
+
+int32_t IndexSubTableFormat4::Builder::NumGlyphs() {
+  return GetOffsetArray()->size() - 1;
+}
+
+int32_t IndexSubTableFormat4::Builder::GlyphLength(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return 0;
+  }
+  int32_t pair_index = FindCodeOffsetPair(glyph_id);
+  if (pair_index == -1) {
+    return 0;
+  }
+  return GetOffsetArray()->at(pair_index + 1).offset() -
+         GetOffsetArray()->at(pair_index).offset();
+}
+
+int32_t IndexSubTableFormat4::Builder::GlyphStartOffset(int32_t glyph_id) {
+  int32_t loca = CheckGlyphRange(glyph_id);
+  if (loca == -1) {
+    return -1;
+  }
+  int32_t pair_index = FindCodeOffsetPair(glyph_id);
+  if (pair_index == -1) {
+    return -1;
+  }
+  return GetOffsetArray()->at(pair_index).offset();
+}
+
+CALLER_ATTACH IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator*
+    IndexSubTableFormat4::Builder::GetIterator() {
+  Ptr<IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator> it =
+      new IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator(this);
+  return it.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat4::Builder*
+IndexSubTableFormat4::Builder::CreateBuilder() {
+  IndexSubTableFormat4BuilderPtr output = new IndexSubTableFormat4::Builder();
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat4::Builder*
+IndexSubTableFormat4::Builder::CreateBuilder(ReadableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  ReadableFontDataPtr new_data;
+  new_data.Attach(down_cast<ReadableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  if (new_data == NULL) {
+    return NULL;
+  }
+  IndexSubTableFormat4BuilderPtr output =
+      new IndexSubTableFormat4::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat4::Builder*
+IndexSubTableFormat4::Builder::CreateBuilder(WritableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  WritableFontDataPtr new_data;
+  new_data.Attach(down_cast<WritableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  IndexSubTableFormat4BuilderPtr output =
+      new IndexSubTableFormat4::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+CALLER_ATTACH FontDataTable* IndexSubTableFormat4::Builder::SubBuildTable(
+    ReadableFontData* data) {
+  IndexSubTableFormat4Ptr output = new IndexSubTableFormat4(
+      data, first_glyph_index(), last_glyph_index());
+  return output.Detach();
+}
+
+void IndexSubTableFormat4::Builder::SubDataSet() {
+  Revert();
+}
+
+int32_t IndexSubTableFormat4::Builder::SubDataSizeToSerialize() {
+  if (offset_pair_array_.empty()) {
+    return InternalReadData()->Length();
+  }
+  return EblcTable::Offset::kIndexSubHeaderLength + DataSize::kULONG +
+         GetOffsetArray()->size() *
+         EblcTable::Offset::kIndexSubTable4_codeOffsetPairLength;
+}
+
+bool IndexSubTableFormat4::Builder::SubReadyToSerialize() {
+  if (!offset_pair_array_.empty()) {
+    return true;
+  }
+  return false;
+}
+
+int32_t IndexSubTableFormat4::Builder::SubSerialize(
+    WritableFontData* new_data) {
+  int32_t size = SerializeIndexSubHeader(new_data);
+  if (!model_changed()) {
+    if (InternalReadData() == NULL) {
+      return size;
+    }
+    ReadableFontDataPtr source;
+    WritableFontDataPtr target;
+    source.Attach(down_cast<ReadableFontData*>(InternalReadData()->Slice(
+        EblcTable::Offset::kIndexSubTable4_glyphArray)));
+    target.Attach(down_cast<WritableFontData*>(new_data->Slice(
+        EblcTable::Offset::kIndexSubTable4_glyphArray)));
+    size += source->CopyTo(target);
+  } else {
+    size += new_data->WriteLong(size, offset_pair_array_.size() - 1);
+    for (std::vector<CodeOffsetPairBuilder>::iterator
+             b = GetOffsetArray()->begin(), e = GetOffsetArray()->end();
+             b != e; b++) {
+      size += new_data->WriteUShort(size, b->glyph_code());
+      size += new_data->WriteUShort(size, b->offset());
+    }
+  }
+  return size;
+}
+
+void IndexSubTableFormat4::Builder::Revert() {
+  offset_pair_array_.clear();
+  IndexSubTable::Builder::Revert();
+}
+
+void IndexSubTableFormat4::Builder::SetOffsetArray(
+    const std::vector<CodeOffsetPairBuilder>& pair_array) {
+  offset_pair_array_.clear();
+  offset_pair_array_ = pair_array;
+  set_model_changed();
+}
+
+IndexSubTableFormat4::Builder::Builder()
+  : IndexSubTable::Builder(EblcTable::Offset::kIndexSubTable4_builderDataSize,
+                           Format::FORMAT_4) {
+}
+
+IndexSubTableFormat4::Builder::Builder(WritableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IndexSubTableFormat4::Builder::Builder(ReadableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+std::vector<IndexSubTableFormat4::CodeOffsetPairBuilder>*
+IndexSubTableFormat4::Builder::GetOffsetArray() {
+  if (offset_pair_array_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &offset_pair_array_;
+}
+
+void IndexSubTableFormat4::Builder::Initialize(ReadableFontData* data) {
+  offset_pair_array_.clear();
+  if (data) {
+    int32_t num_pairs = IndexSubTableFormat4::NumGlyphs(data, 0) + 1;
+    int32_t offset = EblcTable::Offset::kIndexSubTable4_glyphArray;
+    for (int32_t i = 0; i < num_pairs; ++i) {
+      int32_t glyph_code = data->ReadUShort(offset +
+          EblcTable::Offset::kIndexSubTable4_codeOffsetPair_glyphCode);
+      int32_t glyph_offset = data->ReadUShort(offset +
+          EblcTable::Offset::kIndexSubTable4_codeOffsetPair_offset);
+      offset += EblcTable::Offset::kIndexSubTable4_codeOffsetPairLength;
+      CodeOffsetPairBuilder pair_builder(glyph_code, glyph_offset);
+      offset_pair_array_.push_back(pair_builder);
+    }
+  }
+}
+
+int32_t IndexSubTableFormat4::Builder::FindCodeOffsetPair(int32_t glyph_id) {
+  std::vector<CodeOffsetPairBuilder>* pair_list = GetOffsetArray();
+  int32_t location = 0;
+  int32_t bottom = 0;
+  int32_t top = pair_list->size();
+  while (top != bottom) {
+    location = (top + bottom) / 2;
+    CodeOffsetPairBuilder* pair = &(pair_list->at(location));
+    if (glyph_id < pair->glyph_code()) {
+      // location is below current location
+      top = location;
+    } else if (glyph_id > pair->glyph_code()) {
+      // location is above current location
+      bottom = location + 1;
+    } else {
+      return location;
+    }
+  }
+  return -1;
+}
+
+// static
+int32_t IndexSubTableFormat4::Builder::DataLength(
+    ReadableFontData* data,
+    int32_t index_sub_table_offset,
+    int32_t first_glyph_index,
+    int32_t last_glyph_index) {
+  int32_t num_glyphs = IndexSubTableFormat4::NumGlyphs(data,
+                                                       index_sub_table_offset);
+  UNREFERENCED_PARAMETER(first_glyph_index);
+  UNREFERENCED_PARAMETER(last_glyph_index);
+  return EblcTable::Offset::kIndexSubTable4_glyphArray +
+         num_glyphs * EblcTable::Offset::kIndexSubTable4_codeOffsetPair_offset;
+}
+
+
+/******************************************************************************
+ * IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator class
+ ******************************************************************************/
+IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator::BitmapGlyphInfoIterator(
+    IndexSubTableFormat4::Builder* container)
+    : RefIterator<BitmapGlyphInfo, IndexSubTableFormat4::Builder,
+                  IndexSubTable::Builder>(container),
+      code_offset_pair_index_(0) {
+}
+
+bool IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator::HasNext() {
+  if (code_offset_pair_index_ <
+      (int32_t)(container()->GetOffsetArray()->size() - 1)) {
+    return true;
+  }
+  return false;
+}
+
+CALLER_ATTACH BitmapGlyphInfo*
+IndexSubTableFormat4::Builder::BitmapGlyphInfoIterator::Next() {
+  BitmapGlyphInfoPtr output;
+  if (!HasNext()) {
+    // Note: In C++, we do not throw exception when there's no element.
+    return NULL;
+  }
+  std::vector<CodeOffsetPairBuilder>* offset_array =
+      container()->GetOffsetArray();
+  int32_t offset = offset_array->at(code_offset_pair_index_).offset();
+  int32_t next_offset = offset_array->at(code_offset_pair_index_ + 1).offset();
+  int32_t glyph_code = offset_array->at(code_offset_pair_index_).glyph_code();
+  output = new BitmapGlyphInfo(glyph_code,
+                               container()->image_data_offset(),
+                               offset,
+                               next_offset - offset,
+                               container()->image_format());
+  code_offset_pair_index_++;
+  return output.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format4.h b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format4.h
new file mode 100644
index 0000000..efd540f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format4.h
@@ -0,0 +1,135 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT4_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT4_H_
+
+#include "sfntly/table/bitmap/index_sub_table.h"
+
+namespace sfntly {
+
+class IndexSubTableFormat4 : public IndexSubTable,
+                             public RefCounted<IndexSubTableFormat4> {
+ public:
+  class CodeOffsetPair {
+   public:
+    int32_t glyph_code() const { return glyph_code_; }
+    int32_t offset() const { return offset_; }
+
+   protected:
+    CodeOffsetPair(int32_t glyph_code, int32_t offset);
+
+    // TODO(arthurhsu): C++ style guide prohibits protected members.
+    int32_t glyph_code_;
+    int32_t offset_;
+  };
+
+  class CodeOffsetPairBuilder : public CodeOffsetPair {
+   public:
+    CodeOffsetPairBuilder();
+    CodeOffsetPairBuilder(int32_t glyph_code, int32_t offset);
+    void set_glyph_code(int32_t v) { glyph_code_ = v; }
+    void set_offset(int32_t v) { offset_ = v; }
+  };
+
+  class CodeOffsetPairGlyphCodeComparator {
+   public:
+    bool operator()(const CodeOffsetPair& lhs, const CodeOffsetPair& rhs);
+  };
+
+  class Builder : public IndexSubTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    class BitmapGlyphInfoIterator
+        : public RefIterator<BitmapGlyphInfo, Builder, IndexSubTable::Builder> {
+     public:
+      explicit BitmapGlyphInfoIterator(Builder* container);
+      virtual ~BitmapGlyphInfoIterator() {}
+
+      virtual bool HasNext();
+      CALLER_ATTACH virtual BitmapGlyphInfo* Next();
+
+     private:
+      int32_t code_offset_pair_index_;
+    };
+
+    virtual ~Builder();
+    virtual int32_t NumGlyphs();
+    virtual int32_t GlyphLength(int32_t glyph_id);
+    virtual int32_t GlyphStartOffset(int32_t glyph_id);
+    CALLER_ATTACH virtual BitmapGlyphInfoIterator* GetIterator();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    void Revert();
+    void SetOffsetArray(const std::vector<CodeOffsetPairBuilder>& pair_array);
+
+    static CALLER_ATTACH Builder* CreateBuilder();
+    static CALLER_ATTACH Builder* CreateBuilder(ReadableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+    static CALLER_ATTACH Builder* CreateBuilder(WritableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+   private:
+    Builder();
+    Builder(WritableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    Builder(ReadableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    std::vector<CodeOffsetPairBuilder>* GetOffsetArray();
+    void Initialize(ReadableFontData* data);
+    int32_t FindCodeOffsetPair(int32_t glyph_id);
+
+    static int32_t DataLength(ReadableFontData* data,
+                              int32_t index_sub_table_offset,
+                              int32_t first_glyph_index,
+                              int32_t last_glyph_index);
+
+    std::vector<CodeOffsetPairBuilder> offset_pair_array_;
+  };
+
+  virtual ~IndexSubTableFormat4();
+
+  virtual int32_t NumGlyphs();
+  virtual int32_t GlyphStartOffset(int32_t glyph_id);
+  virtual int32_t GlyphLength(int32_t glyph_id);
+
+ private:
+  IndexSubTableFormat4(ReadableFontData* data,
+                       int32_t first_glyph_index,
+                       int32_t last_glyph_index);
+
+  int32_t FindCodeOffsetPair(int32_t glyph_id);
+  static int32_t NumGlyphs(ReadableFontData* data, int32_t table_offset);
+
+  friend class Builder;
+};
+typedef Ptr<IndexSubTableFormat4> IndexSubTableFormat4Ptr;
+typedef Ptr<IndexSubTableFormat4::Builder> IndexSubTableFormat4BuilderPtr;
+typedef std::vector<IndexSubTableFormat4::CodeOffsetPairBuilder>
+            CodeOffsetPairBuilderList;
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT4_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format5.cc b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format5.cc
new file mode 100644
index 0000000..0ca21fe
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format5.cc
@@ -0,0 +1,347 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/index_sub_table_format5.h"
+
+#include <algorithm>
+
+#include "sfntly/table/bitmap/eblc_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * IndexSubTableFormat5 class
+ ******************************************************************************/
+IndexSubTableFormat5::~IndexSubTableFormat5() {
+}
+
+int32_t IndexSubTableFormat5::NumGlyphs() {
+  return NumGlyphs(data_, 0);
+}
+
+int32_t IndexSubTableFormat5::GlyphStartOffset(int32_t glyph_id) {
+  int32_t check = CheckGlyphRange(glyph_id);
+  if (check == -1) {
+    return -1;
+  }
+  int32_t loca = ReadFontData()->SearchUShort(
+      EblcTable::Offset::kIndexSubTable5_glyphArray,
+      DataSize::kUSHORT,
+      NumGlyphs(),
+      glyph_id);
+  if (loca == -1) {
+    return loca;
+  }
+  return loca * ImageSize();
+}
+
+int32_t IndexSubTableFormat5::GlyphLength(int32_t glyph_id) {
+  int32_t check = CheckGlyphRange(glyph_id);
+  if (check == -1) {
+    return 0;
+  }
+  return image_size_;
+}
+
+int32_t IndexSubTableFormat5::ImageSize() {
+  return data_->ReadULongAsInt(EblcTable::Offset::kIndexSubTable5_imageSize);
+}
+
+CALLER_ATTACH BigGlyphMetrics* IndexSubTableFormat5::BigMetrics() {
+  ReadableFontDataPtr data;
+  data.Attach(down_cast<ReadableFontData*>(data_->Slice(
+      EblcTable::Offset::kIndexSubTable5_bigGlyphMetrics,
+      BigGlyphMetrics::Offset::kMetricsLength)));
+  BigGlyphMetricsPtr output = new BigGlyphMetrics(data);
+  return output.Detach();
+}
+
+IndexSubTableFormat5::IndexSubTableFormat5(ReadableFontData* data,
+                                           int32_t first_glyph_index,
+                                           int32_t last_glyph_index)
+    : IndexSubTable(data, first_glyph_index, last_glyph_index) {
+  image_size_ = data_->ReadULongAsInt(
+      EblcTable::Offset::kIndexSubTable5_imageSize);
+}
+
+// static
+int32_t IndexSubTableFormat5::NumGlyphs(ReadableFontData* data,
+                                        int32_t table_offset) {
+  int32_t num_glyphs = data->ReadULongAsInt(table_offset +
+      EblcTable::Offset::kIndexSubTable5_numGlyphs);
+  return num_glyphs;
+}
+
+/******************************************************************************
+ * IndexSubTableFormat5::Builder class
+ ******************************************************************************/
+IndexSubTableFormat5::Builder::~Builder() {
+}
+
+int32_t IndexSubTableFormat5::Builder::NumGlyphs() {
+  return GetGlyphArray()->size();
+}
+
+int32_t IndexSubTableFormat5::Builder::GlyphLength(int32_t glyph_id) {
+  UNREFERENCED_PARAMETER(glyph_id);
+  return ImageSize();
+}
+
+int32_t IndexSubTableFormat5::Builder::GlyphStartOffset(int32_t glyph_id) {
+  int32_t check = CheckGlyphRange(glyph_id);
+  if (check == -1) {
+    return -1;
+  }
+  IntegerList* glyph_array = GetGlyphArray();
+  IntegerList::iterator it = std::find(glyph_array->begin(),
+                                       glyph_array->end(),
+                                       glyph_id);
+  if (it == glyph_array->end()) {
+    return -1;
+  }
+  return (it - glyph_array->begin()) * ImageSize();
+}
+
+CALLER_ATTACH IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator*
+    IndexSubTableFormat5::Builder::GetIterator() {
+  Ptr<IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator> it =
+      new IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator(this);
+  return it.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat5::Builder*
+IndexSubTableFormat5::Builder::CreateBuilder() {
+  IndexSubTableFormat5BuilderPtr output = new IndexSubTableFormat5::Builder();
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat5::Builder*
+IndexSubTableFormat5::Builder::CreateBuilder(ReadableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  ReadableFontDataPtr new_data;
+  new_data.Attach(down_cast<ReadableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  if (new_data == NULL) {
+    return NULL;
+  }
+  IndexSubTableFormat5BuilderPtr output =
+      new IndexSubTableFormat5::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+// static
+CALLER_ATTACH IndexSubTableFormat5::Builder*
+IndexSubTableFormat5::Builder::CreateBuilder(WritableFontData* data,
+                                             int32_t index_sub_table_offset,
+                                             int32_t first_glyph_index,
+                                             int32_t last_glyph_index) {
+  int32_t length = Builder::DataLength(data,
+                                       index_sub_table_offset,
+                                       first_glyph_index,
+                                       last_glyph_index);
+  WritableFontDataPtr new_data;
+  new_data.Attach(down_cast<WritableFontData*>(
+      data->Slice(index_sub_table_offset, length)));
+  IndexSubTableFormat5BuilderPtr output =
+      new IndexSubTableFormat5::Builder(new_data,
+                                        first_glyph_index,
+                                        last_glyph_index);
+  return output.Detach();
+}
+
+CALLER_ATTACH FontDataTable* IndexSubTableFormat5::Builder::SubBuildTable(
+    ReadableFontData* data) {
+  IndexSubTableFormat5Ptr output = new IndexSubTableFormat5(
+      data, first_glyph_index(), last_glyph_index());
+  return output.Detach();
+}
+
+void IndexSubTableFormat5::Builder::SubDataSet() {
+  Revert();
+}
+
+int32_t IndexSubTableFormat5::Builder::SubDataSizeToSerialize() {
+  if (glyph_array_.empty()) {
+    return InternalReadData()->Length();
+  }
+  return EblcTable::Offset::kIndexSubTable5_builderDataSize +
+         glyph_array_.size() * DataSize::kUSHORT;
+}
+
+bool IndexSubTableFormat5::Builder::SubReadyToSerialize() {
+  if (!glyph_array_.empty()) {
+    return true;
+  }
+  return false;
+}
+
+int32_t IndexSubTableFormat5::Builder::SubSerialize(
+    WritableFontData* new_data) {
+  int32_t size = SerializeIndexSubHeader(new_data);
+  if (!model_changed()) {
+    ReadableFontDataPtr source;
+    WritableFontDataPtr target;
+    source.Attach(down_cast<ReadableFontData*>(InternalReadData()->Slice(
+        EblcTable::Offset::kIndexSubTable5_imageSize)));
+    target.Attach(down_cast<WritableFontData*>(new_data->Slice(
+        EblcTable::Offset::kIndexSubTable5_imageSize)));
+    size += source->CopyTo(target);
+  } else {
+    size += new_data->WriteULong(EblcTable::Offset::kIndexSubTable5_imageSize,
+                                 ImageSize());
+    WritableFontDataPtr slice;
+    slice.Attach(down_cast<WritableFontData*>(new_data->Slice(size)));
+    size += BigMetrics()->SubSerialize(slice);
+    size += new_data->WriteULong(size, glyph_array_.size());
+    for (IntegerList::iterator b = glyph_array_.begin(), e = glyph_array_.end();
+                               b != e; b++) {
+      size += new_data->WriteUShort(size, *b);
+    }
+  }
+  return size;
+}
+
+int32_t IndexSubTableFormat5::Builder::ImageSize() {
+  return InternalReadData()->ReadULongAsInt(
+      EblcTable::Offset::kIndexSubTable5_imageSize);
+}
+
+void IndexSubTableFormat5::Builder::SetImageSize(int32_t image_size) {
+  InternalWriteData()->WriteULong(
+      EblcTable::Offset::kIndexSubTable5_imageSize, image_size);
+}
+
+BigGlyphMetrics::Builder* IndexSubTableFormat5::Builder::BigMetrics() {
+  if (metrics_ == NULL) {
+    WritableFontDataPtr data;
+    data.Attach(down_cast<WritableFontData*>(InternalWriteData()->Slice(
+        EblcTable::Offset::kIndexSubTable5_bigGlyphMetrics,
+        BigGlyphMetrics::Offset::kMetricsLength)));
+    metrics_ = new BigGlyphMetrics::Builder(data);
+    set_model_changed();
+  }
+  return metrics_;
+}
+
+IntegerList* IndexSubTableFormat5::Builder::GlyphArray() {
+  return GetGlyphArray();
+}
+
+void IndexSubTableFormat5::Builder::SetGlyphArray(const IntegerList& v) {
+  glyph_array_.clear();
+  glyph_array_ = v;
+  set_model_changed();
+}
+
+void IndexSubTableFormat5::Builder::Revert() {
+  glyph_array_.clear();
+  IndexSubTable::Builder::Revert();
+}
+
+IndexSubTableFormat5::Builder::Builder()
+    : IndexSubTable::Builder(EblcTable::Offset::kIndexSubTable5_builderDataSize,
+                             IndexSubTable::Format::FORMAT_5) {
+}
+
+IndexSubTableFormat5::Builder::Builder(WritableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IndexSubTableFormat5::Builder::Builder(ReadableFontData* data,
+                                       int32_t first_glyph_index,
+                                       int32_t last_glyph_index)
+    : IndexSubTable::Builder(data, first_glyph_index, last_glyph_index) {
+}
+
+IntegerList* IndexSubTableFormat5::Builder::GetGlyphArray() {
+  if (glyph_array_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &glyph_array_;
+}
+
+void IndexSubTableFormat5::Builder::Initialize(ReadableFontData* data) {
+  glyph_array_.clear();
+  if (data) {
+    int32_t num_glyphs = IndexSubTableFormat5::NumGlyphs(data, 0);
+    for (int32_t i = 0; i < num_glyphs; ++i) {
+      glyph_array_.push_back(data->ReadUShort(
+          EblcTable::Offset::kIndexSubTable5_glyphArray +
+          i * DataSize::kUSHORT));
+    }
+  }
+}
+
+// static
+int32_t IndexSubTableFormat5::Builder::DataLength(
+    ReadableFontData* data,
+    int32_t index_sub_table_offset,
+    int32_t first_glyph_index,
+    int32_t last_glyph_index) {
+  int32_t num_glyphs = IndexSubTableFormat5::NumGlyphs(data,
+                                                       index_sub_table_offset);
+  UNREFERENCED_PARAMETER(first_glyph_index);
+  UNREFERENCED_PARAMETER(last_glyph_index);
+  return EblcTable::Offset::kIndexSubTable5_glyphArray +
+         num_glyphs * DataSize::kUSHORT;
+}
+
+/******************************************************************************
+ * IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator class
+ ******************************************************************************/
+IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator::BitmapGlyphInfoIterator(
+    IndexSubTableFormat5::Builder* container)
+    : RefIterator<BitmapGlyphInfo, IndexSubTableFormat5::Builder,
+                  IndexSubTable::Builder>(container),
+      offset_index_(0) {
+}
+
+bool IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator::HasNext() {
+  if (offset_index_ < (int32_t)(container()->GetGlyphArray()->size())) {
+    return true;
+  }
+  return false;
+}
+
+CALLER_ATTACH BitmapGlyphInfo*
+IndexSubTableFormat5::Builder::BitmapGlyphInfoIterator::Next() {
+  BitmapGlyphInfoPtr output;
+  if (!HasNext()) {
+    // Note: In C++, we do not throw exception when there's no element.
+    return NULL;
+  }
+  output = new BitmapGlyphInfo(container()->GetGlyphArray()->at(offset_index_),
+                               container()->image_data_offset(),
+                               offset_index_ * container()->ImageSize(),
+                               container()->ImageSize(),
+                               container()->image_format());
+  offset_index_++;
+  return output.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format5.h b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format5.h
new file mode 100644
index 0000000..a39e88c
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/index_sub_table_format5.h
@@ -0,0 +1,118 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT5_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT5_H_
+
+#include "sfntly/table/bitmap/big_glyph_metrics.h"
+#include "sfntly/table/bitmap/index_sub_table.h"
+
+namespace sfntly {
+
+class IndexSubTableFormat5 : public IndexSubTable,
+                             public RefCounted<IndexSubTableFormat5> {
+ public:
+  class Builder : public IndexSubTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    class BitmapGlyphInfoIterator
+        : public RefIterator<BitmapGlyphInfo, Builder, IndexSubTable::Builder> {
+     public:
+      explicit BitmapGlyphInfoIterator(Builder* container);
+      virtual ~BitmapGlyphInfoIterator() {}
+
+      virtual bool HasNext();
+      CALLER_ATTACH virtual BitmapGlyphInfo* Next();
+
+     private:
+      int32_t offset_index_;
+    };
+    virtual ~Builder();
+    virtual int32_t NumGlyphs();
+    virtual int32_t GlyphLength(int32_t glyph_id);
+    virtual int32_t GlyphStartOffset(int32_t glyph_id);
+    CALLER_ATTACH virtual BitmapGlyphInfoIterator* GetIterator();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+    int32_t ImageSize();
+    void SetImageSize(int32_t image_size);
+    BigGlyphMetrics::Builder* BigMetrics();
+    IntegerList* GlyphArray();
+    void SetGlyphArray(const IntegerList& v);
+
+    static CALLER_ATTACH Builder* CreateBuilder();
+    static CALLER_ATTACH Builder* CreateBuilder(ReadableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+    static CALLER_ATTACH Builder* CreateBuilder(WritableFontData* data,
+                                                int32_t index_sub_table_offset,
+                                                int32_t first_glyph_index,
+                                                int32_t last_glyph_index);
+   protected:
+    void Revert();
+
+   private:
+    Builder();
+    Builder(WritableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+    Builder(ReadableFontData* data,
+            int32_t first_glyph_index,
+            int32_t last_glyph_index);
+
+    IntegerList* GetGlyphArray();
+    void Initialize(ReadableFontData* data);
+
+    static int32_t DataLength(ReadableFontData* data,
+                              int32_t index_sub_table_offset,
+                              int32_t first_glyph_index,
+                              int32_t last_glyph_index);
+
+    IntegerList glyph_array_;
+    BigGlyphMetricsBuilderPtr metrics_;
+  };
+  virtual ~IndexSubTableFormat5();
+
+  virtual int32_t NumGlyphs();
+  virtual int32_t GlyphStartOffset(int32_t glyph_id);
+  virtual int32_t GlyphLength(int32_t glyph_id);
+
+  int32_t ImageSize();
+  CALLER_ATTACH BigGlyphMetrics* BigMetrics();
+
+ private:
+  IndexSubTableFormat5(ReadableFontData* data,
+                       int32_t first_glyph_index,
+                       int32_t last_glyph_index);
+
+  static int32_t NumGlyphs(ReadableFontData* dta, int32_t table_offset);
+
+  int32_t image_size_;
+
+  friend class Builder;
+};
+typedef Ptr<IndexSubTableFormat5> IndexSubTableFormat5Ptr;
+typedef Ptr<IndexSubTableFormat5::Builder> IndexSubTableFormat5BuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_INDEX_SUBTABLE_FORMAT5_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/simple_bitmap_glyph.cc b/sfntly/cpp/src/sfntly/table/bitmap/simple_bitmap_glyph.cc
new file mode 100644
index 0000000..87031a1
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/simple_bitmap_glyph.cc
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/simple_bitmap_glyph.h"
+
+namespace sfntly {
+
+SimpleBitmapGlyph::SimpleBitmapGlyph(ReadableFontData* data, int32_t format)
+    : BitmapGlyph(data, format) {
+}
+
+SimpleBitmapGlyph::~SimpleBitmapGlyph() {
+}
+
+SimpleBitmapGlyph::Builder::Builder(ReadableFontData* data, int32_t format)
+    : BitmapGlyph::Builder(data, format) {
+}
+
+SimpleBitmapGlyph::Builder::Builder(WritableFontData* data, int32_t format)
+    : BitmapGlyph::Builder(data, format) {
+}
+
+SimpleBitmapGlyph::Builder::~Builder() {
+}
+
+CALLER_ATTACH FontDataTable*
+SimpleBitmapGlyph::Builder::SubBuildTable(ReadableFontData* data) {
+  Ptr<SimpleBitmapGlyph> glyph = new SimpleBitmapGlyph(data, format());
+  return glyph.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/simple_bitmap_glyph.h b/sfntly/cpp/src/sfntly/table/bitmap/simple_bitmap_glyph.h
new file mode 100644
index 0000000..56ede10
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/simple_bitmap_glyph.h
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0  = the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_SIMPLE_BITMAP_GLYPH_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_SIMPLE_BITMAP_GLYPH_H_
+
+#include "sfntly/table/bitmap/bitmap_glyph.h"
+
+namespace sfntly {
+
+class SimpleBitmapGlyph : public BitmapGlyph,
+                          public RefCounted<SimpleBitmapGlyph> {
+ public:
+  class Builder : public BitmapGlyph::Builder,
+                  public RefCounted<Builder> {
+   public:
+    Builder(WritableFontData* data, int32_t format);
+    Builder(ReadableFontData* data, int32_t format);
+    virtual ~Builder();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+  };
+
+  SimpleBitmapGlyph(ReadableFontData* data, int32_t format);
+  virtual ~SimpleBitmapGlyph();
+};
+typedef Ptr<SimpleBitmapGlyph> SimpleBitmapGlyphPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_SIMPLE_BITMAP_GLYPH_H_
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/small_glyph_metrics.cc b/sfntly/cpp/src/sfntly/table/bitmap/small_glyph_metrics.cc
new file mode 100644
index 0000000..0f3c1e9
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/small_glyph_metrics.cc
@@ -0,0 +1,126 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/bitmap/small_glyph_metrics.h"
+
+namespace sfntly {
+/******************************************************************************
+ * SmallGlyphMetrics class
+ ******************************************************************************/
+SmallGlyphMetrics::SmallGlyphMetrics(ReadableFontData* data)
+    : GlyphMetrics(data) {
+}
+
+SmallGlyphMetrics::~SmallGlyphMetrics() {
+}
+
+int32_t SmallGlyphMetrics::Height() {
+  return data_->ReadByte(Offset::kHeight);
+}
+
+int32_t SmallGlyphMetrics::Width() {
+  return data_->ReadByte(Offset::kWidth);
+}
+
+int32_t SmallGlyphMetrics::BearingX() {
+  return data_->ReadByte(Offset::kBearingX);
+}
+
+int32_t SmallGlyphMetrics::BearingY() {
+  return data_->ReadByte(Offset::kBearingY);
+}
+
+int32_t SmallGlyphMetrics::Advance() {
+  return data_->ReadByte(Offset::kAdvance);
+}
+
+/******************************************************************************
+ * SmallGlyphMetrics::Builder class
+ ******************************************************************************/
+SmallGlyphMetrics::Builder::Builder(WritableFontData* data)
+    : GlyphMetrics::Builder(data) {
+}
+
+SmallGlyphMetrics::Builder::Builder(ReadableFontData* data)
+    : GlyphMetrics::Builder(data) {
+}
+
+SmallGlyphMetrics::Builder::~Builder() {
+}
+
+int32_t SmallGlyphMetrics::Builder::Height() {
+  return InternalReadData()->ReadByte(Offset::kHeight);
+}
+
+void SmallGlyphMetrics::Builder::SetHeight(byte_t height) {
+  InternalWriteData()->WriteByte(Offset::kHeight, height);
+}
+
+int32_t SmallGlyphMetrics::Builder::Width() {
+  return InternalReadData()->ReadByte(Offset::kWidth);
+}
+
+void SmallGlyphMetrics::Builder::SetWidth(byte_t width) {
+  InternalWriteData()->WriteByte(Offset::kWidth, width);
+}
+
+int32_t SmallGlyphMetrics::Builder::BearingX() {
+  return InternalReadData()->ReadByte(Offset::kBearingX);
+}
+
+void SmallGlyphMetrics::Builder::SetBearingX(byte_t bearing) {
+  InternalWriteData()->WriteByte(Offset::kBearingX, bearing);
+}
+
+int32_t SmallGlyphMetrics::Builder::BearingY() {
+  return InternalReadData()->ReadByte(Offset::kBearingY);
+}
+
+void SmallGlyphMetrics::Builder::SetBearingY(byte_t bearing) {
+  InternalWriteData()->WriteByte(Offset::kBearingY, bearing);
+}
+
+int32_t SmallGlyphMetrics::Builder::Advance() {
+  return InternalReadData()->ReadByte(Offset::kAdvance);
+}
+
+void SmallGlyphMetrics::Builder::SetAdvance(byte_t advance) {
+  InternalWriteData()->WriteByte(Offset::kAdvance, advance);
+}
+
+CALLER_ATTACH FontDataTable*
+    SmallGlyphMetrics::Builder::SubBuildTable(ReadableFontData* data) {
+  SmallGlyphMetricsPtr output = new SmallGlyphMetrics(data);
+  return output.Detach();
+}
+
+void SmallGlyphMetrics::Builder::SubDataSet() {
+  // NOP.
+}
+
+int32_t SmallGlyphMetrics::Builder::SubDataSizeToSerialize() {
+  return 0;
+}
+
+bool SmallGlyphMetrics::Builder::SubReadyToSerialize() {
+  return false;
+}
+
+int32_t SmallGlyphMetrics::Builder::SubSerialize(WritableFontData* new_data) {
+  return Data()->CopyTo(new_data);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/bitmap/small_glyph_metrics.h b/sfntly/cpp/src/sfntly/table/bitmap/small_glyph_metrics.h
new file mode 100644
index 0000000..ea13720
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/bitmap/small_glyph_metrics.h
@@ -0,0 +1,79 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_SMALL_GLYPH_METRICS_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_SMALL_GLYPH_METRICS_H_
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/table/bitmap/glyph_metrics.h"
+
+namespace sfntly {
+
+class SmallGlyphMetrics : public GlyphMetrics,
+                          public RefCounted<SmallGlyphMetrics> {
+ public:
+  struct Offset {
+    enum {
+      kMetricsLength = 5,
+      kHeight = 0,
+      kWidth = 1,
+      kBearingX = 2,
+      kBearingY = 3,
+      kAdvance = 4,
+    };
+  };
+
+  class Builder : public GlyphMetrics::Builder,
+                  public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    explicit Builder(WritableFontData* data);
+    explicit Builder(ReadableFontData* data);
+    virtual ~Builder();
+
+    int32_t Height();
+    void SetHeight(byte_t height);
+    int32_t Width();
+    void SetWidth(byte_t width);
+    int32_t BearingX();
+    void SetBearingX(byte_t bearing);
+    int32_t BearingY();
+    void SetBearingY(byte_t bearing);
+    int32_t Advance();
+    void SetAdvance(byte_t advance);
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+  };
+
+  explicit SmallGlyphMetrics(ReadableFontData* data);
+  virtual ~SmallGlyphMetrics();
+
+  int32_t Height();
+  int32_t Width();
+  int32_t BearingX();
+  int32_t BearingY();
+  int32_t Advance();
+};
+typedef Ptr<SmallGlyphMetrics> SmallGlyphMetricsPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BITMAP_SMALL_GLYPH_METRICS_H_
diff --git a/sfntly/cpp/src/sfntly/table/byte_array_table_builder.cc b/sfntly/cpp/src/sfntly/table/byte_array_table_builder.cc
new file mode 100644
index 0000000..631a05f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/byte_array_table_builder.cc
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/byte_array_table_builder.h"
+
+namespace sfntly {
+
+ByteArrayTableBuilder::~ByteArrayTableBuilder() {}
+
+int32_t ByteArrayTableBuilder::ByteValue(int32_t index) {
+  ReadableFontDataPtr data = InternalReadData();
+  if (data == NULL) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("No font data for the table");
+#endif
+    return -1;
+  }
+  return data->ReadByte(index);
+}
+
+void ByteArrayTableBuilder::SetByteValue(int32_t index, byte_t b) {
+  WritableFontDataPtr data = InternalWriteData();
+  if (data == NULL) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("No font data for the table");
+#endif
+    return;
+  }
+  data->WriteByte(index, b);
+}
+
+int32_t ByteArrayTableBuilder::ByteCount() {
+  ReadableFontDataPtr data = InternalReadData();
+  if (data == NULL) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IOException("No font data for the table");
+#endif
+    return 0;
+  }
+  return data->Length();
+}
+
+ByteArrayTableBuilder::ByteArrayTableBuilder(Header* header,
+                                               WritableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+ByteArrayTableBuilder::ByteArrayTableBuilder(Header* header,
+                                               ReadableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+ByteArrayTableBuilder::ByteArrayTableBuilder(Header* header)
+    : TableBasedTableBuilder(header) {
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/byte_array_table_builder.h b/sfntly/cpp/src/sfntly/table/byte_array_table_builder.h
new file mode 100644
index 0000000..42d27a8
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/byte_array_table_builder.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_BYTE_ARRAY_TABLE_BUILDER_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_BYTE_ARRAY_TABLE_BUILDER_H_
+
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+// An abstract builder base for byte array based tables.
+class ByteArrayTableBuilder : public TableBasedTableBuilder {
+ public:
+  virtual ~ByteArrayTableBuilder();
+
+  // Get the byte value at the specified index. The index is relative to the
+  // start of the table.
+  // @param index index relative to the start of the table
+  // @return byte value at the given index
+  virtual int32_t ByteValue(int32_t index);
+
+  // Set the byte value at the specified index. The index is relative to the
+  // start of the table.
+  // @param index index relative to the start of the table
+  // @param b byte value to set
+  virtual void SetByteValue(int32_t index, byte_t b);
+
+  // Get the number of bytes set for this table. It may include padding bytes at
+  // the end.
+  virtual int32_t ByteCount();
+
+ protected:
+  ByteArrayTableBuilder(Header* header, WritableFontData* data);
+  ByteArrayTableBuilder(Header* header, ReadableFontData* data);
+  explicit ByteArrayTableBuilder(Header* header);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BYTE_ARRAY_TABLE_BUILDER_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/cmap_table.cc b/sfntly/cpp/src/sfntly/table/core/cmap_table.cc
new file mode 100644
index 0000000..1c83d2e
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/cmap_table.cc
@@ -0,0 +1,1287 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// type.h needs to be included first because of building issues on Windows
+// Type aliases we delcare are defined in other headers and make the build
+// fail otherwise.
+#include "sfntly/port/type.h"
+#include "sfntly/table/core/cmap_table.h"
+
+#include <stdio.h>
+#include <stdlib.h>
+
+#include <utility>
+
+#include "sfntly/font.h"
+#include "sfntly/math/font_math.h"
+#include "sfntly/port/endian.h"
+#include "sfntly/port/exception_type.h"
+#include "sfntly/table/core/name_table.h"
+
+namespace sfntly {
+
+const int32_t CMapTable::NOTDEF = 0;
+
+CMapTable::CMapId CMapTable::WINDOWS_BMP = {
+  PlatformId::kWindows,
+  WindowsEncodingId::kUnicodeUCS2
+};
+CMapTable::CMapId CMapTable::WINDOWS_UCS4 = {
+  PlatformId::kWindows,
+  WindowsEncodingId::kUnicodeUCS4
+};
+CMapTable::CMapId CMapTable::MAC_ROMAN = {
+  PlatformId::kWindows,
+  MacintoshEncodingId::kRoman
+};
+
+/******************************************************************************
+ * CMapTable class
+ ******************************************************************************/
+CMapTable::CMapTable(Header* header, ReadableFontData* data)
+  : SubTableContainerTable(header, data) {
+}
+
+CMapTable::~CMapTable() {}
+
+CALLER_ATTACH CMapTable::CMap* CMapTable::GetCMap(const int32_t index) {
+  if (index < 0 || index > NumCMaps()) {
+#ifndef SFNTLY_NO_EXCEPTION
+    throw IndexOutOfBoundException("Requested CMap index is out of bounds.");
+#else
+    return NULL;
+#endif
+  }
+  int32_t platform_id = PlatformId(index);
+  int32_t encoding_id = EncodingId(index);
+  CMapId cmap_id = NewCMapId(platform_id, encoding_id);
+  int32_t offset_ = Offset(index);
+  Ptr<FontDataTable::Builder> cmap_builder =
+      (CMap::Builder::GetBuilder(data_, offset_, cmap_id));
+  if (!cmap_builder) {
+#ifndef SFNTLY_NO_EXCEPTION
+    throw NoSuchElementException("Cannot find builder for requested CMap.");
+#else
+    return NULL;
+#endif
+  }
+  return down_cast<CMapTable::CMap*>(cmap_builder->Build());
+}
+
+CALLER_ATTACH CMapTable::CMap* CMapTable::GetCMap(const int32_t platform_id,
+                                                  const int32_t encoding_id) {
+  return GetCMap(NewCMapId(platform_id, encoding_id));
+}
+
+CALLER_ATTACH CMapTable::CMap*
+CMapTable::GetCMap(const CMapTable::CMapId cmap_id) {
+  CMapIdFilter id_filter(cmap_id);
+  CMapIterator cmap_iterator(this, &id_filter);
+  // There can only be one cmap with a particular CMapId
+  if (cmap_iterator.HasNext()) {
+    Ptr<CMapTable::CMap> cmap;
+    cmap.Attach(cmap_iterator.Next());
+    return cmap.Detach();
+  }
+#ifndef SFNTLY_NO_EXCEPTION
+  throw NoSuchElementException();
+#else
+  return NULL;
+#endif
+}
+
+int32_t CMapTable::Version() {
+  return data_->ReadUShort(Offset::kVersion);
+}
+
+int32_t CMapTable::NumCMaps() {
+  return data_->ReadUShort(Offset::kNumTables);
+}
+
+CMapTable::CMapId CMapTable::GetCMapId(int32_t index) {
+  return NewCMapId(PlatformId(index), EncodingId(index));
+}
+
+int32_t CMapTable::PlatformId(int32_t index) {
+  return data_->ReadUShort(Offset::kEncodingRecordPlatformId +
+                           OffsetForEncodingRecord(index));
+}
+
+int32_t CMapTable::EncodingId(int32_t index) {
+  return data_->ReadUShort(Offset::kEncodingRecordEncodingId +
+                           OffsetForEncodingRecord(index));
+}
+
+int32_t CMapTable::Offset(int32_t index) {
+  return data_->ReadULongAsInt(Offset::kEncodingRecordOffset +
+                               OffsetForEncodingRecord(index));
+}
+
+int32_t CMapTable::OffsetForEncodingRecord(int32_t index) {
+  return Offset::kEncodingRecordStart + index * Offset::kEncodingRecordSize;
+}
+
+CMapTable::CMapId CMapTable::NewCMapId(int32_t platform_id,
+                                       int32_t encoding_id) {
+  CMapId result;
+  result.platform_id = platform_id;
+  result.encoding_id = encoding_id;
+  return result;
+}
+
+CMapTable::CMapId CMapTable::NewCMapId(const CMapId& obj) {
+  CMapId result;
+  result.platform_id = obj.platform_id;
+  result.encoding_id = obj.encoding_id;
+  return result;
+}
+
+/******************************************************************************
+ * CMapTable::CMapIterator class
+ ******************************************************************************/
+CMapTable::CMapIterator::CMapIterator(CMapTable* table,
+                                      const CMapFilter* filter)
+    : table_index_(0), filter_(filter), table_(table) {
+}
+
+bool CMapTable::CMapIterator::HasNext() {
+  if (!filter_) {
+    if (table_index_ < table_->NumCMaps()) {
+      return true;
+    }
+    return false;
+  }
+
+  for (; table_index_ < table_->NumCMaps(); ++table_index_) {
+    if (filter_->accept(table_->GetCMapId(table_index_))) {
+      return true;
+    }
+  }
+  return false;
+}
+
+CALLER_ATTACH CMapTable::CMap* CMapTable::CMapIterator::Next() {
+  if (!HasNext()) {
+#ifndef SFNTLY_NO_EXCEPTION
+    throw NoSuchElementException();
+#else
+    return NULL;
+#endif
+  }
+  CMapPtr next_cmap;
+  next_cmap.Attach(table_->GetCMap(table_index_++));
+  if (next_cmap == NULL) {
+#ifndef SFNTLY_NO_EXCEPTION
+    throw NoSuchElementException("Error during the creation of the CMap");
+#else
+    return NULL;
+#endif
+  }
+  return next_cmap.Detach();
+}
+
+/******************************************************************************
+ * CMapTable::CMapId class
+ ******************************************************************************/
+
+/******************************************************************************
+ * CMapTable::CMapIdComparator class
+ ******************************************************************************/
+
+bool CMapTable::CMapIdComparator::operator()(const CMapId& lhs,
+                                             const CMapId& rhs) const {
+  return ((lhs.platform_id << 8 | lhs.encoding_id) >
+      (rhs.platform_id << 8 | rhs.encoding_id));
+}
+
+/******************************************************************************
+ * CMapTable::CMapIdFilter class
+ ******************************************************************************/
+CMapTable::CMapIdFilter::CMapIdFilter(const CMapId wanted_id)
+    : wanted_id_(wanted_id),
+      comparator_(NULL) {
+}
+
+CMapTable::CMapIdFilter::CMapIdFilter(const CMapId wanted_id,
+                                      const CMapIdComparator* comparator)
+    : wanted_id_(wanted_id),
+      comparator_(comparator) {
+}
+
+bool CMapTable::CMapIdFilter::accept(const CMapId& cmap_id) const {
+  if (!comparator_)
+    return wanted_id_ == cmap_id;
+  return (*comparator_)(wanted_id_, cmap_id);
+}
+
+/******************************************************************************
+ * CMapTable::CMap class
+ ******************************************************************************/
+CMapTable::CMap::CMap(ReadableFontData* data, int32_t format,
+                      const CMapId& cmap_id)
+    : SubTable(data), format_(format), cmap_id_(cmap_id) {
+}
+
+CMapTable::CMap::~CMap() {
+}
+
+/******************************************************************************
+ * CMapTable::CMap::Builder class
+ ******************************************************************************/
+CMapTable::CMap::Builder::~Builder() {
+}
+
+CALLER_ATTACH CMapTable::CMap::Builder*
+    CMapTable::CMap::Builder::GetBuilder(ReadableFontData* data, int32_t offset,
+                                         const CMapId& cmap_id) {
+  // NOT IMPLEMENTED: Java enum value validation
+  int32_t format = data->ReadUShort(offset);
+  CMapBuilderPtr builder;
+  switch (format) {
+    case CMapFormat::kFormat0:
+      builder.Attach(CMapFormat0::Builder::NewInstance(data, offset, cmap_id));
+      break;
+    case CMapFormat::kFormat2:
+#if defined (SFNTLY_DEBUG_CMAP)
+      fprintf(stderr, "Requesting Format2 builder, but it's unsupported; "
+              "returning NULL\n");
+#endif
+      break;
+    case CMapFormat::kFormat4:
+      builder.Attach(CMapFormat4::Builder::NewInstance(data, offset, cmap_id));
+      break;
+    default:
+#ifdef SFNTLY_DEBUG_CMAP
+      fprintf(stderr, "Unknown builder format requested\n");
+#endif
+      break;
+  }
+  return builder.Detach();
+}
+
+CALLER_ATTACH CMapTable::CMap::Builder*
+CMapTable::CMap::Builder::GetBuilder(int32_t format, const CMapId& cmap_id) {
+  Ptr<CMapTable::CMap::Builder> builder;
+  switch (format) {
+    case CMapFormat::kFormat0:
+      builder.Attach(CMapFormat0::Builder::NewInstance(cmap_id));
+      break;
+    case CMapFormat::kFormat2:
+#if defined (SFNTLY_DEBUG_CMAP)
+      fprintf(stderr, "Requesting Format2 builder, but it's unsupported; "
+              "returning NULL\n");
+#endif
+      break;
+    case CMapFormat::kFormat4:
+      builder.Attach(CMapFormat4::Builder::NewInstance(cmap_id));
+      break;
+    default:
+#ifdef SFNTLY_DEBUG_CMAP
+      fprintf(stderr, "Unknown builder format requested\n");
+#endif
+      break;
+  }
+  return builder.Detach();
+}
+
+CMapTable::CMap::Builder::Builder(ReadableFontData* data,
+                                  int32_t format,
+                                  const CMapId& cmap_id)
+    : SubTable::Builder(data),
+      format_(format),
+      cmap_id_(cmap_id),
+      language_(0) {
+}
+
+CMapTable::CMap::Builder::Builder(WritableFontData* data,
+                                  int32_t format,
+                                  const CMapId& cmap_id)
+    : SubTable::Builder(data),
+      format_(format),
+      cmap_id_(cmap_id),
+      language_(0) {
+}
+
+int32_t CMapTable::CMap::Builder::SubSerialize(WritableFontData* new_data) {
+  return InternalReadData()->CopyTo(new_data);
+}
+
+bool CMapTable::CMap::Builder::SubReadyToSerialize() {
+  return true;
+}
+
+int32_t CMapTable::CMap::Builder::SubDataSizeToSerialize() {
+  ReadableFontDataPtr read_data = InternalReadData();
+  if (!read_data)
+    return 0;
+  return read_data->Length();
+}
+
+void CMapTable::CMap::Builder::SubDataSet() {
+  // NOP
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat0
+ ******************************************************************************/
+CMapTable::CMapFormat0::~CMapFormat0() {
+}
+
+int32_t CMapTable::CMapFormat0::Language() {
+  return 0;
+}
+
+int32_t CMapTable::CMapFormat0::GlyphId(int32_t character) {
+  if (character < 0 || character > 255) {
+    return CMapTable::NOTDEF;
+  }
+  return data_->ReadUByte(character + Offset::kFormat0GlyphIdArray);
+}
+
+CMapTable::CMapFormat0::CMapFormat0(ReadableFontData* data,
+                                    const CMapId& cmap_id)
+    : CMap(data, CMapFormat::kFormat0, cmap_id) {
+}
+
+CMapTable::CMap::CharacterIterator* CMapTable::CMapFormat0::Iterator() {
+  return new CMapTable::CMapFormat0::CharacterIterator(0, 0xff);
+}
+
+
+/******************************************************************************
+ * CMapTable::CMapFormat0::CharacterIterator
+ ******************************************************************************/
+CMapTable::CMapFormat0::CharacterIterator::CharacterIterator(int32_t start,
+                                                             int32_t end)
+    : character_(start),
+    max_character_(end) {
+}
+
+CMapTable::CMapFormat0::CharacterIterator::~CharacterIterator() {}
+
+bool CMapTable::CMapFormat0::CharacterIterator::HasNext() {
+  return character_ < max_character_;
+}
+
+int32_t CMapTable::CMapFormat0::CharacterIterator::Next() {
+  if (HasNext())
+    return character_++;
+#ifndef SFNTLY_NO_EXCEPTION
+  throw NoSuchElementException("No more characters to iterate.");
+#endif
+  return -1;
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat0::Builder
+ ******************************************************************************/
+// static
+CALLER_ATTACH CMapTable::CMapFormat0::Builder*
+CMapTable::CMapFormat0::Builder::NewInstance(WritableFontData* data,
+                                             int32_t offset,
+                                             const CMapId& cmap_id) {
+  WritableFontDataPtr wdata;
+  if (data) {
+    wdata.Attach(down_cast<WritableFontData*>(
+        data->Slice(offset,
+                    data->ReadUShort(offset + Offset::kFormat0Length))));
+  }
+  return new Builder(wdata, CMapFormat::kFormat0, cmap_id);
+}
+
+// static
+CALLER_ATTACH CMapTable::CMapFormat0::Builder*
+CMapTable::CMapFormat0::Builder::NewInstance(ReadableFontData* data,
+                                             int32_t offset,
+                                             const CMapId& cmap_id) {
+  ReadableFontDataPtr rdata;
+  if (data) {
+    rdata.Attach(down_cast<ReadableFontData*>(
+        data->Slice(offset,
+                    data->ReadUShort(offset + Offset::kFormat0Length))));
+  }
+  return new Builder(rdata, CMapFormat::kFormat0, cmap_id);
+}
+
+// static
+CALLER_ATTACH CMapTable::CMapFormat0::Builder*
+CMapTable::CMapFormat0::Builder::NewInstance(const CMapId& cmap_id) {
+  return new Builder(cmap_id);
+}
+
+// Always call NewInstance instead of the constructor for creating a new builder
+// object! This refactoring avoids memory leaks when slicing the font data.
+CMapTable::CMapFormat0::Builder::Builder(WritableFontData* data, int32_t offset,
+                                         const CMapId& cmap_id)
+    : CMapTable::CMap::Builder(data, CMapFormat::kFormat0, cmap_id) {
+  UNREFERENCED_PARAMETER(offset);
+}
+
+CMapTable::CMapFormat0::Builder::Builder(
+    ReadableFontData* data,
+    int32_t offset,
+    const CMapId& cmap_id)
+    : CMapTable::CMap::Builder(data, CMapFormat::kFormat0, cmap_id) {
+  UNREFERENCED_PARAMETER(offset);
+}
+
+CMapTable::CMapFormat0::Builder::Builder(const CMapId& cmap_id)
+    : CMap::Builder(reinterpret_cast<ReadableFontData*>(NULL),
+                    CMapFormat::kFormat0,
+                    cmap_id) {
+}
+
+CMapTable::CMapFormat0::Builder::~Builder() {
+}
+
+CALLER_ATTACH FontDataTable*
+    CMapTable::CMapFormat0::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new CMapFormat0(data, cmap_id());
+  return table.Detach();
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat2
+ ******************************************************************************/
+CMapTable::CMapFormat2::~CMapFormat2() {
+}
+
+int32_t CMapTable::CMapFormat2::Language() {
+  return 0;
+}
+
+int32_t CMapTable::CMapFormat2::GlyphId(int32_t character) {
+  if (character > 0xffff) {
+    return CMapTable::NOTDEF;
+  }
+
+  uint32_t c = ToBE32(character);
+  byte_t high_byte = (c >> 8) & 0xff;
+  byte_t low_byte = c & 0xff;
+  int32_t offset = SubHeaderOffset(high_byte);
+
+  if (offset == 0) {
+    low_byte = high_byte;
+    high_byte = 0;
+  }
+
+  int32_t first_code = FirstCode(high_byte);
+  int32_t entry_count = EntryCount(high_byte);
+
+  if (low_byte < first_code || low_byte >= first_code + entry_count) {
+    return CMapTable::NOTDEF;
+  }
+
+  int32_t id_range_offset = IdRangeOffset(high_byte);
+
+  // position of idRangeOffset + value of idRangeOffset + index for low byte
+  // = firstcode
+  int32_t p_location = (offset + Offset::kFormat2SubHeader_idRangeOffset) +
+      id_range_offset +
+      (low_byte - first_code) * DataSize::kUSHORT;
+  int p = data_->ReadUShort(p_location);
+  if (p == 0) {
+    return CMapTable::NOTDEF;
+  }
+
+  if (offset == 0) {
+    return p;
+  }
+  int id_delta = IdDelta(high_byte);
+  return (p + id_delta) % 65536;
+}
+
+int32_t CMapTable::CMapFormat2::BytesConsumed(int32_t character) {
+  uint32_t c = ToBE32(character);
+  int32_t high_byte = (c >> 8) & 0xff;
+  int32_t offset = SubHeaderOffset(high_byte);
+  return (offset == 0) ? 1 : 2;
+}
+
+CMapTable::CMapFormat2::CMapFormat2(ReadableFontData* data,
+                                    const CMapId& cmap_id)
+    : CMap(data, CMapFormat::kFormat2, cmap_id) {
+}
+
+int32_t CMapTable::CMapFormat2::SubHeaderOffset(int32_t sub_header_index) {
+  return data_->ReadUShort(Offset::kFormat2SubHeaderKeys +
+                           sub_header_index * DataSize::kUSHORT);
+}
+
+int32_t CMapTable::CMapFormat2::FirstCode(int32_t sub_header_index) {
+  int32_t sub_header_offset = SubHeaderOffset(sub_header_index);
+  return data_->ReadUShort(sub_header_offset +
+                           Offset::kFormat2SubHeaderKeys +
+                           Offset::kFormat2SubHeader_firstCode);
+}
+
+int32_t CMapTable::CMapFormat2::EntryCount(int32_t sub_header_index) {
+  int32_t sub_header_offset = SubHeaderOffset(sub_header_index);
+  return data_->ReadUShort(sub_header_offset +
+                           Offset::kFormat2SubHeaderKeys +
+                           Offset::kFormat2SubHeader_entryCount);
+}
+
+int32_t CMapTable::CMapFormat2::IdRangeOffset(int32_t sub_header_index) {
+  int32_t sub_header_offset = SubHeaderOffset(sub_header_index);
+  return data_->ReadUShort(sub_header_offset +
+                           Offset::kFormat2SubHeaderKeys +
+                           Offset::kFormat2SubHeader_idRangeOffset);
+}
+
+int32_t CMapTable::CMapFormat2::IdDelta(int32_t sub_header_index) {
+  int32_t sub_header_offset = SubHeaderOffset(sub_header_index);
+  return data_->ReadUShort(sub_header_offset +
+                           Offset::kFormat2SubHeaderKeys +
+                           Offset::kFormat2SubHeader_idDelta);
+}
+
+CMapTable::CMap::CharacterIterator* CMapTable::CMapFormat2::Iterator() {
+  // UNIMPLEMENTED
+  return NULL;
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat2::Builder
+ ******************************************************************************/
+CMapTable::CMapFormat2::Builder::Builder(WritableFontData* data,
+                                         int32_t offset,
+                                         const CMapId& cmap_id)
+    : CMapTable::CMap::Builder(data ? down_cast<WritableFontData*>(
+                                   data->Slice(offset, data->ReadUShort(
+                                       offset + Offset::kFormat0Length)))
+                               : reinterpret_cast<WritableFontData*>(NULL),
+                               CMapFormat::kFormat2, cmap_id) {
+  // TODO(arthurhsu): FIXIT: heavy lifting and leak, need fix.
+}
+
+CMapTable::CMapFormat2::Builder::Builder(ReadableFontData* data,
+                                         int32_t offset,
+                                         const CMapId& cmap_id)
+    : CMapTable::CMap::Builder(data ? down_cast<ReadableFontData*>(
+                                   data->Slice(offset, data->ReadUShort(
+                                       offset + Offset::kFormat0Length)))
+                               : reinterpret_cast<ReadableFontData*>(NULL),
+                               CMapFormat::kFormat2, cmap_id) {
+  // TODO(arthurhsu): FIXIT: heavy lifting and leak, need fix.
+}
+
+CMapTable::CMapFormat2::Builder::~Builder() {
+}
+
+CALLER_ATTACH FontDataTable*
+    CMapTable::CMapFormat2::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new CMapFormat2(data, cmap_id());
+  return table.Detach();
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat4
+ ******************************************************************************/
+CMapTable::CMapFormat4::CMapFormat4(ReadableFontData* data,
+                                    const CMapId& cmap_id)
+    : CMap(data, CMapFormat::kFormat4, cmap_id),
+      seg_count_(SegCount(data)),
+      start_code_offset_(StartCodeOffset(seg_count_)),
+      id_delta_offset_(IdDeltaOffset(seg_count_)),
+      glyph_id_array_offset_(GlyphIdArrayOffset(seg_count_)) {
+}
+
+CMapTable::CMapFormat4::~CMapFormat4() {
+}
+
+int32_t CMapTable::CMapFormat4::GlyphId(int32_t character) {
+  int32_t segment = data_->SearchUShort(StartCodeOffset(seg_count_),
+                                        DataSize::kUSHORT,
+                                        Offset::kFormat4EndCount,
+                                        DataSize::kUSHORT,
+                                        seg_count_,
+                                        character);
+  if (segment == -1) {
+    return CMapTable::NOTDEF;
+  }
+  int32_t start_code = StartCode(segment);
+  return RetrieveGlyphId(segment, start_code, character);
+}
+
+int32_t CMapTable::CMapFormat4::RetrieveGlyphId(int32_t segment,
+                                                int32_t start_code,
+                                                int32_t character) {
+  if (character < start_code) {
+    return CMapTable::NOTDEF;
+  }
+  int32_t id_range_offset = IdRangeOffset(segment);
+  if (id_range_offset == 0) {
+    return (character + IdDelta(segment)) % 65536;
+  }
+  return data_->ReadUShort(id_range_offset +
+                           IdRangeOffsetLocation(segment) +
+                           2 * (character - start_code));
+}
+
+int32_t CMapTable::CMapFormat4::seg_count() {
+  return seg_count_;
+}
+
+int32_t CMapTable::CMapFormat4::Length() {
+  return Length(data_);
+}
+
+int32_t CMapTable::CMapFormat4::StartCode(int32_t segment) {
+  if (!IsValidIndex(segment)) {
+    return -1;
+  }
+  return StartCode(data_.p_, seg_count_, segment);
+}
+
+// static
+int32_t CMapTable::CMapFormat4::Language(ReadableFontData* data) {
+  int32_t language = data->ReadUShort(Offset::kFormat4Language);
+  return language;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::Length(ReadableFontData* data) {
+  int32_t length = data->ReadUShort(Offset::kFormat4Length);
+  return length;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::SegCount(ReadableFontData* data) {
+  int32_t seg_count = data->ReadUShort(Offset::kFormat4SegCountX2) / 2;
+  return seg_count;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::StartCode(ReadableFontData* data,
+                                          int32_t seg_count,
+                                          int32_t index) {
+  int32_t start_code = data->ReadUShort(StartCodeOffset(seg_count) +
+                                        index * DataSize::kUSHORT);
+  return start_code;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::StartCodeOffset(int32_t seg_count) {
+  int32_t start_code_offset = Offset::kFormat4EndCount +
+      (seg_count + 1) * DataSize::kUSHORT;
+  return start_code_offset;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::EndCode(ReadableFontData* data,
+                                        int32_t seg_count,
+                                        int32_t index) {
+  UNREFERENCED_PARAMETER(seg_count);
+  int32_t end_code = data->ReadUShort(Offset::kFormat4EndCount +
+                                      index * DataSize::kUSHORT);
+  return end_code;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::IdDelta(ReadableFontData* data,
+                                        int32_t seg_count,
+                                        int32_t index) {
+  int32_t id_delta = data->ReadUShort(IdDeltaOffset(seg_count) +
+                                      index * DataSize::kUSHORT);
+  return id_delta;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::IdDeltaOffset(int32_t seg_count) {
+  int32_t id_delta_offset =
+      Offset::kFormat4EndCount + (2 * seg_count + 1) * DataSize::kUSHORT;
+  return id_delta_offset;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::IdRangeOffset(ReadableFontData* data,
+                                              int32_t seg_count,
+                                              int32_t index) {
+  int32_t id_range_offset =
+      data->ReadUShort(IdRangeOffsetOffset(seg_count)
+                       + index * DataSize::kUSHORT);
+  return id_range_offset;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::IdRangeOffsetOffset(int32_t seg_count) {
+  int32_t id_range_offset_offset =
+      Offset::kFormat4EndCount + (2 * seg_count + 1) * DataSize::kUSHORT +
+      seg_count * DataSize::kSHORT;
+  return id_range_offset_offset;
+}
+
+// static
+int32_t CMapTable::CMapFormat4::GlyphIdArrayOffset(int32_t seg_count) {
+  int32_t glyph_id_array_offset =
+      Offset::kFormat4EndCount + (3 * seg_count + 1) * DataSize::kUSHORT +
+      seg_count * DataSize::kSHORT;
+  return glyph_id_array_offset;
+}
+
+int32_t CMapTable::CMapFormat4::EndCode(int32_t segment) {
+  if (IsValidIndex(segment)) {
+    return EndCode(data_, seg_count_, segment);
+  }
+#if defined (SFNTLY_NO_EXCEPTION)
+  return -1;
+#else
+  throw IllegalArgumentException();
+#endif
+}
+
+bool CMapTable::CMapFormat4::IsValidIndex(int32_t segment) {
+  if (segment < 0 || segment >= seg_count_) {
+#if defined (SFNTLY_NO_EXCEPTION)
+    return false;
+#else
+    throw IllegalArgumentException();
+#endif
+  }
+  return true;
+}
+
+int32_t CMapTable::CMapFormat4::IdDelta(int32_t segment) {
+  if (IsValidIndex(segment))
+    return IdDelta(data_, seg_count_, segment);
+  return -1;
+}
+
+int32_t CMapTable::CMapFormat4::IdRangeOffset(int32_t segment) {
+  if (IsValidIndex(segment))
+    return data_->ReadUShort(IdRangeOffsetLocation(segment));
+  return -1;
+}
+
+int32_t CMapTable::CMapFormat4::IdRangeOffsetLocation(int32_t segment) {
+  if (IsValidIndex(segment))
+    return IdRangeOffsetOffset(seg_count_) + segment * DataSize::kUSHORT;
+  return -1;
+}
+
+int32_t CMapTable::CMapFormat4::GlyphIdArray(int32_t index) {
+  return data_->ReadUShort(glyph_id_array_offset_ + index * DataSize::kUSHORT);
+}
+
+int32_t CMapTable::CMapFormat4::Language() {
+  return Language(data_);
+}
+
+
+CMapTable::CMap::CharacterIterator* CMapTable::CMapFormat4::Iterator() {
+  return new CharacterIterator(this);
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat4::CharacterIterator class
+ ******************************************************************************/
+CMapTable::CMapFormat4::CharacterIterator::CharacterIterator(
+    CMapFormat4* parent)
+    : parent_(parent),
+      segment_index_(0),
+      first_char_in_segment_(-1),
+      last_char_in_segment_(-1),
+      next_char_(-1),
+      next_char_set_(false) {
+}
+
+bool CMapTable::CMapFormat4::CharacterIterator::HasNext() {
+  if (next_char_set_)
+    return true;
+  while (segment_index_ < parent_->seg_count_) {
+    if (first_char_in_segment_ < 0) {
+      first_char_in_segment_ = parent_->StartCode(segment_index_);
+      last_char_in_segment_ = parent_->EndCode(segment_index_);
+      next_char_ = first_char_in_segment_;
+      next_char_set_ = true;
+      return true;
+    }
+    if (next_char_ < last_char_in_segment_) {
+      next_char_++;
+      next_char_set_ = true;
+      return true;
+    }
+    segment_index_++;
+    first_char_in_segment_ = -1;
+  }
+  return false;
+}
+
+int32_t CMapTable::CMapFormat4::CharacterIterator::Next() {
+  if (!next_char_set_) {
+    if (!HasNext()) {
+#if defined (SFNTLY_NO_EXCEPTION)
+      return -1;
+#else
+      throw NoSuchElementException("No more characters to iterate.");
+#endif
+    }
+  }
+  next_char_set_ = false;
+  return next_char_;
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat4::Builder::Segment class
+ ******************************************************************************/
+CMapTable::CMapFormat4::Builder::Segment::Segment() {}
+
+CMapTable::CMapFormat4::Builder::Segment::Segment(Segment* other)
+    : start_count_(other->start_count_),
+      end_count_(other->end_count_),
+      id_delta_(other->id_delta_),
+      id_range_offset_(other->id_range_offset_) {
+}
+
+CMapTable::CMapFormat4::Builder::Segment::Segment(int32_t start_count,
+                                                  int32_t end_count,
+                                                  int32_t id_delta,
+                                                  int32_t id_range_offset)
+    : start_count_(start_count),
+      end_count_(end_count),
+      id_delta_(id_delta),
+      id_range_offset_(id_range_offset) {
+}
+
+CMapTable::CMapFormat4::Builder::Segment::~Segment() {}
+
+int32_t CMapTable::CMapFormat4::Builder::Segment::start_count() {
+  return start_count_;
+}
+
+void
+CMapTable::CMapFormat4::Builder::Segment::set_start_count(int32_t start_count) {
+  start_count_ = start_count;
+}
+
+int32_t CMapTable::CMapFormat4::Builder::Segment::end_count() {
+  return end_count_;
+}
+
+void
+CMapTable::CMapFormat4::Builder::Segment::set_end_count(int32_t end_count) {
+  end_count_ = end_count;
+}
+
+int32_t CMapTable::CMapFormat4::Builder::Segment::id_delta() {
+  return id_delta_;
+}
+
+void
+CMapTable::CMapFormat4::Builder::Segment::set_id_delta(int32_t id_delta) {
+  id_delta_ = id_delta;
+}
+
+int32_t CMapTable::CMapFormat4::Builder::Segment::id_range_offset() {
+  return id_range_offset_;
+}
+
+void
+CMapTable::CMapFormat4::Builder::Segment::
+set_id_range_offset(int32_t id_range_offset) {
+  id_range_offset_ = id_range_offset;
+}
+
+// static
+CALLER_ATTACH SegmentList*
+CMapTable::CMapFormat4::Builder::Segment::DeepCopy(SegmentList* original) {
+  SegmentList* list = new SegmentList;
+  for (SegmentList::iterator it = original->begin(),
+           e = original->end(); it != e; ++it) {
+    list->push_back(*it);
+  }
+  return list;
+}
+
+/******************************************************************************
+ * CMapTable::CMapFormat4::Builder class
+ ******************************************************************************/
+CALLER_ATTACH CMapTable::CMapFormat4::Builder*
+CMapTable::CMapFormat4::Builder::NewInstance(ReadableFontData* data,
+                                             int32_t offset,
+                                             const CMapId& cmap_id) {
+  ReadableFontDataPtr rdata;
+  if (data) {
+    rdata.Attach
+        (down_cast<ReadableFontData*>
+         (data->Slice(offset,
+                      data->ReadUShort(offset + Offset::kFormat4Length))));
+  }
+  return new Builder(rdata, CMapFormat::kFormat4, cmap_id);
+}
+
+CALLER_ATTACH CMapTable::CMapFormat4::Builder*
+CMapTable::CMapFormat4::Builder::NewInstance(WritableFontData* data,
+                                             int32_t offset,
+                                             const CMapId& cmap_id) {
+  WritableFontDataPtr wdata;
+  if (data) {
+    wdata.Attach
+        (down_cast<WritableFontData*>
+         (data->Slice(offset,
+                      data->ReadUShort(offset + Offset::kFormat4Length))));
+  }
+  return new Builder(wdata, CMapFormat::kFormat4, cmap_id);
+}
+
+CALLER_ATTACH CMapTable::CMapFormat4::Builder*
+CMapTable::CMapFormat4::Builder::NewInstance(const CMapId& cmap_id) {
+  return new Builder(cmap_id);
+}
+
+CMapTable::CMapFormat4::Builder::Builder(ReadableFontData* data, int32_t offset,
+                                         const CMapId& cmap_id)
+    : CMap::Builder(data, CMapFormat::kFormat4, cmap_id) {
+  UNREFERENCED_PARAMETER(offset);
+}
+
+CMapTable::CMapFormat4::Builder::Builder(WritableFontData* data, int32_t offset,
+                                         const CMapId& cmap_id)
+    : CMap::Builder(data, CMapFormat::kFormat4, cmap_id) {
+  UNREFERENCED_PARAMETER(offset);
+}
+
+CMapTable::CMapFormat4::Builder::Builder(SegmentList* segments,
+                                         IntegerList* glyph_id_array,
+                                         const CMapId& cmap_id)
+    : CMap::Builder(reinterpret_cast<ReadableFontData*>(NULL),
+                    CMapFormat::kFormat4, cmap_id),
+      segments_(segments->begin(), segments->end()),
+      glyph_id_array_(glyph_id_array->begin(), glyph_id_array->end()) {
+  set_model_changed();
+}
+
+CMapTable::CMapFormat4::Builder::Builder(const CMapId& cmap_id)
+    : CMap::Builder(reinterpret_cast<ReadableFontData*>(NULL),
+                    CMapFormat::kFormat4, cmap_id) {
+}
+
+CMapTable::CMapFormat4::Builder::~Builder() {}
+
+void CMapTable::CMapFormat4::Builder::Initialize(ReadableFontData* data) {
+  if (data == NULL || data->Length() == 0)
+    return;
+
+  // build segments
+  int32_t seg_count = CMapFormat4::SegCount(data);
+  for (int32_t index = 0; index < seg_count; ++index) {
+    Ptr<Segment> segment = new Segment;
+    segment->set_start_count(CMapFormat4::StartCode(data, seg_count, index));
+#if defined SFNTLY_DEBUG_CMAP
+    fprintf(stderr, "Segment %d; start %d\n", index, segment->start_count());
+#endif
+    segment->set_end_count(CMapFormat4::EndCode(data, seg_count, index));
+    segment->set_id_delta(CMapFormat4::IdDelta(data, seg_count, index));
+    segment->set_id_range_offset(CMapFormat4::IdRangeOffset(data,
+                                                           seg_count,
+                                                           index));
+    segments_.push_back(segment);
+  }
+
+  // build glyph id array
+  int32_t glyph_id_array_offset = CMapFormat4::GlyphIdArrayOffset(seg_count);
+  int32_t glyph_id_array_length =
+      (CMapFormat4::Length(data) - glyph_id_array_offset)
+      / DataSize::kUSHORT;
+  fprintf(stderr, "id array size %d\n", glyph_id_array_length);
+  for (int32_t i = 0; i < glyph_id_array_length; i += DataSize::kUSHORT) {
+    glyph_id_array_.push_back(data->ReadUShort(glyph_id_array_offset + i));
+  }
+}
+
+SegmentList* CMapTable::CMapFormat4::Builder::segments() {
+  if (segments_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &segments_;
+}
+
+void CMapTable::CMapFormat4::Builder::set_segments(SegmentList* segments) {
+  segments_.assign(segments->begin(), segments->end());
+  set_model_changed();
+}
+
+IntegerList* CMapTable::CMapFormat4::Builder::glyph_id_array() {
+  if (glyph_id_array_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &glyph_id_array_;
+}
+
+void CMapTable::CMapFormat4::Builder::
+set_glyph_id_array(IntegerList* glyph_id_array) {
+  glyph_id_array_.assign(glyph_id_array->begin(), glyph_id_array->end());
+  set_model_changed();
+}
+
+CALLER_ATTACH FontDataTable*
+CMapTable::CMapFormat4::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new CMapFormat4(data, cmap_id());
+  return table.Detach();
+}
+
+void CMapTable::CMapFormat4::Builder::SubDataSet() {
+  segments_.clear();
+  glyph_id_array_.clear();
+  set_model_changed();
+}
+
+int32_t CMapTable::CMapFormat4::Builder::SubDataSizeToSerialize() {
+  if (!model_changed()) {
+    return CMap::Builder::SubDataSizeToSerialize();
+  }
+  int32_t size = Offset::kFormat4FixedSize + segments_.size()
+      * (3 * DataSize::kUSHORT + DataSize::kSHORT)
+      + glyph_id_array_.size() * DataSize::kSHORT;
+  return size;
+}
+
+bool CMapTable::CMapFormat4::Builder::SubReadyToSerialize() {
+  if (!model_changed()) {
+    return CMap::Builder::SubReadyToSerialize();
+  }
+  if (!segments()->empty()) {
+    return true;
+  }
+  return false;
+}
+
+int32_t
+CMapTable::CMapFormat4::Builder::SubSerialize(WritableFontData* new_data) {
+  if (!model_changed()) {
+    return CMap::Builder::SubSerialize(new_data);
+  }
+  int32_t index = 0;
+  index += new_data->WriteUShort(index, CMapFormat::kFormat4);
+  index += DataSize::kUSHORT;  // length - write this at the end
+  index += new_data->WriteUShort(index, language());
+
+  int32_t seg_count = segments_.size();
+  index += new_data->WriteUShort(index, seg_count * 2);
+  int32_t log2_seg_count = FontMath::Log2(seg_count);
+  int32_t search_range = 1 << (log2_seg_count + 1);
+  index += new_data->WriteUShort(index, search_range);
+  int32_t entry_selector = log2_seg_count;
+  index += new_data->WriteUShort(index, entry_selector);
+  int32_t range_shift = 2 * seg_count - search_range;
+  index += new_data->WriteUShort(index, range_shift);
+
+  for (int32_t i = 0; i < seg_count; ++i) {
+    index += new_data->WriteUShort(index, segments_[i]->end_count());
+  }
+  index += new_data->WriteUShort(index, 0);  // reserved ushort
+  for (int32_t i = 0; i < seg_count; ++i) {
+#if defined SFNTLY_DEBUG_CMAP
+    fprintf(stderr, "Segment %d; start %d\n", i, segments_[i]->start_count());
+#endif
+    index += new_data->WriteUShort(index, segments_[i]->start_count());
+  }
+  for (int32_t i = 0; i < seg_count; ++i) {
+    index += new_data->WriteShort(index, segments_[i]->id_delta());
+  }
+  for (int32_t i = 0; i < seg_count; ++i) {
+    index += new_data->WriteUShort(index, segments_[i]->id_range_offset());
+  }
+
+#if defined SFNTLY_DEBUG_CMAP
+  fprintf(stderr, "Glyph id array size %lu\n", glyph_id_array_.size());
+#endif
+  for (size_t i = 0; i < glyph_id_array_.size(); ++i) {
+    index += new_data->WriteUShort(index, glyph_id_array_[i]);
+  }
+
+  new_data->WriteUShort(Offset::kFormat4Length, index);
+  return index;
+}
+
+/******************************************************************************
+ * CMapTable::Builder class
+ ******************************************************************************/
+CMapTable::Builder::Builder(Header* header, WritableFontData* data)
+    : SubTableContainerTable::Builder(header, data), version_(0) {
+}
+
+CMapTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : SubTableContainerTable::Builder(header, data), version_(0) {
+}
+
+CMapTable::Builder::~Builder() {
+}
+
+int32_t CMapTable::Builder::SubSerialize(WritableFontData* new_data) {
+  int32_t size = new_data->WriteUShort(CMapTable::Offset::kVersion,
+                                       version_);
+  size += new_data->WriteUShort(CMapTable::Offset::kNumTables,
+                                GetCMapBuilders()->size());
+
+  int32_t index_offset = size;
+  size += GetCMapBuilders()->size() * CMapTable::Offset::kEncodingRecordSize;
+  for (CMapBuilderMap::iterator it = GetCMapBuilders()->begin(),
+           e = GetCMapBuilders()->end(); it != e; ++it) {
+    CMapBuilderPtr b = it->second;
+    // header entry
+    index_offset += new_data->WriteUShort(index_offset, b->platform_id());
+    index_offset += new_data->WriteUShort(index_offset, b->encoding_id());
+    index_offset += new_data->WriteULong(index_offset, size);
+
+    // cmap
+    FontDataPtr slice;
+    slice.Attach(new_data->Slice(size));
+    size += b->SubSerialize(down_cast<WritableFontData*>(slice.p_));
+  }
+  return size;
+}
+
+bool CMapTable::Builder::SubReadyToSerialize() {
+  if (GetCMapBuilders()->empty())
+    return false;
+
+  // check each table
+  for (CMapBuilderMap::iterator it = GetCMapBuilders()->begin(),
+           e = GetCMapBuilders()->end(); it != e; ++it) {
+    if (!it->second->SubReadyToSerialize())
+      return false;
+  }
+  return true;
+}
+
+int32_t CMapTable::Builder::SubDataSizeToSerialize() {
+  if (GetCMapBuilders()->empty())
+    return 0;
+
+  bool variable = false;
+  int32_t size = CMapTable::Offset::kEncodingRecordStart +
+      GetCMapBuilders()->size() * CMapTable::Offset::kEncodingRecordSize;
+
+  // calculate size of each table
+  for (CMapBuilderMap::iterator it = GetCMapBuilders()->begin(),
+           e = GetCMapBuilders()->end(); it != e; ++it) {
+    int32_t cmap_size = it->second->SubDataSizeToSerialize();
+    size += abs(cmap_size);
+    variable |= cmap_size <= 0;
+  }
+  return variable ? -size : size;
+}
+
+void CMapTable::Builder::SubDataSet() {
+  GetCMapBuilders()->clear();
+  Table::Builder::set_model_changed();
+}
+
+CALLER_ATTACH FontDataTable*
+    CMapTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new CMapTable(header(), data);
+  return table.Detach();
+}
+
+CALLER_ATTACH CMapTable::Builder*
+    CMapTable::Builder::CreateBuilder(Header* header,
+                                      WritableFontData* data) {
+  Ptr<CMapTable::Builder> builder;
+  builder = new CMapTable::Builder(header, data);
+  return builder.Detach();
+}
+
+// static
+CALLER_ATTACH CMapTable::CMap::Builder*
+    CMapTable::Builder::CMapBuilder(ReadableFontData* data, int32_t index) {
+  if (index < 0 || index > NumCMaps(data)) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException(
+              "CMap table is outside of the bounds of the known tables.");
+#endif
+    return NULL;
+  }
+
+  int32_t platform_id = data->ReadUShort(Offset::kEncodingRecordPlatformId +
+                                         OffsetForEncodingRecord(index));
+  int32_t encoding_id = data->ReadUShort(Offset::kEncodingRecordEncodingId +
+                                         OffsetForEncodingRecord(index));
+  int32_t offset = data->ReadULongAsInt(Offset::kEncodingRecordOffset +
+                                        OffsetForEncodingRecord(index));
+  return CMap::Builder::GetBuilder(data, offset,
+                                   NewCMapId(platform_id, encoding_id));
+}
+
+// static
+int32_t CMapTable::Builder::NumCMaps(ReadableFontData* data) {
+  if (data == NULL) {
+    return 0;
+  }
+  return data->ReadUShort(Offset::kNumTables);
+}
+
+int32_t CMapTable::Builder::NumCMaps() {
+  return GetCMapBuilders()->size();
+}
+
+void CMapTable::Builder::Initialize(ReadableFontData* data) {
+  int32_t num_cmaps = NumCMaps(data);
+  for (int32_t i = 0; i < num_cmaps; ++i) {
+    CMapTable::CMap::Builder* cmap_builder = CMapBuilder(data, i);
+    if (!cmap_builder)
+      continue;
+    cmap_builders_[cmap_builder->cmap_id()] = cmap_builder;
+  }
+}
+
+CMapTable::CMap::Builder* CMapTable::Builder::NewCMapBuilder(
+    const CMapId& cmap_id,
+    ReadableFontData* data) {
+  Ptr<WritableFontData> wfd;
+  wfd.Attach(WritableFontData::CreateWritableFontData(data->Size()));
+  data->CopyTo(wfd.p_);
+  CMapTable::CMapBuilderPtr builder;
+  builder.Attach(CMap::Builder::GetBuilder(wfd.p_, 0, cmap_id));
+  CMapBuilderMap* cmap_builders = CMapTable::Builder::GetCMapBuilders();
+  cmap_builders->insert(std::make_pair(cmap_id, builder.p_));
+  return builder.Detach();
+}
+
+CMapTable::CMap::Builder*
+CMapTable::Builder::NewCMapBuilder(int32_t format, const CMapId& cmap_id) {
+  Ptr<CMapTable::CMap::Builder> cmap_builder;
+  cmap_builder.Attach(CMap::Builder::GetBuilder(format, cmap_id));
+  CMapBuilderMap* cmap_builders = CMapTable::Builder::GetCMapBuilders();
+  cmap_builders->insert(std::make_pair(cmap_id, cmap_builder.p_));
+  return cmap_builder.Detach();
+}
+
+CMapTable::CMap::Builder*
+CMapTable::Builder::CMapBuilder(const CMapId& cmap_id) {
+  CMapBuilderMap* cmap_builders = this->GetCMapBuilders();
+  CMapBuilderMap::iterator builder = cmap_builders->find(cmap_id);
+  if (builder != cmap_builders->end())
+    return builder->second;
+#ifndef SFNTLY_NO_EXCEPTION
+  throw NoSuchElementException("No builder found for cmap_id");
+#else
+  return NULL;
+#endif
+}
+
+CMapTable::CMapBuilderMap* CMapTable::Builder::GetCMapBuilders() {
+  if (cmap_builders_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &cmap_builders_;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/cmap_table.h b/sfntly/cpp/src/sfntly/table/core/cmap_table.h
new file mode 100644
index 0000000..b264b07
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/cmap_table.h
@@ -0,0 +1,709 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_CMAP_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_CMAP_TABLE_H_
+
+// type.h needs to be included first because of building issues on Windows
+// Type aliases we delcare are defined in other headers and make the build
+// fail otherwise.
+#include "sfntly/port/type.h"
+#include <vector>
+#include <map>
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/table/subtable.h"
+#include "sfntly/table/subtable_container_table.h"
+
+namespace sfntly {
+
+// CMap subtable formats
+struct CMapFormat {
+  enum {
+    kFormat0 = 0,
+    kFormat2 = 2,
+    kFormat4 = 4,
+    kFormat6 = 6,
+    kFormat8 = 8,
+    kFormat10 = 10,
+    kFormat12 = 12,
+    kFormat13 = 13,
+    kFormat14 = 14
+  };
+};
+
+// A CMap table
+class CMapTable : public SubTableContainerTable, public RefCounted<CMapTable> {
+public:
+  // CMapTable::CMapId
+  struct CMapId {
+    int32_t platform_id;
+    int32_t encoding_id;
+    bool operator==(const CMapId& obj) const {
+      return platform_id == obj.platform_id && encoding_id == obj.encoding_id;
+    }
+  };
+  static CMapId WINDOWS_BMP;
+  static CMapId WINDOWS_UCS4;
+  static CMapId MAC_ROMAN;
+
+  // CMapTable::CMapIdComparator
+  class CMapIdComparator {
+   public:
+    bool operator()(const CMapId& lhs, const CMapId& rhs) const;
+  };
+
+  // A filter on cmap
+  // CMapTable::CMapFilter
+  class CMapFilter {
+   public:
+    // Test on whether the cmap is acceptable or not
+    // @param cmap_id the id of the cmap
+    // @return true if the cmap is acceptable; false otherwise
+    virtual bool accept(const CMapId& cmap_id) const = 0;
+    // Make gcc -Wnon-virtual-dtor happy.
+    virtual ~CMapFilter() {}
+  };
+
+  // Filters CMaps by CMapId to implement CMapTable::get()
+  // wanted_id is the CMap we'd like to find.
+  // We compare the current CMap to it either by equality (==) or using a
+  // comparator.
+  // CMapTable::CMapIdFilter
+  class CMapIdFilter : public CMapFilter {
+   public:
+    explicit CMapIdFilter(const CMapId wanted_id);
+    CMapIdFilter(const CMapId wanted_id,
+                 const CMapIdComparator* comparator);
+    ~CMapIdFilter() {}
+    virtual bool accept(const CMapId& cmap_id) const;
+   private:
+    CMapIdFilter& operator=(const CMapIdFilter& that);
+    const CMapId wanted_id_;
+    const CMapIdComparator *comparator_;
+  };
+
+  // The abstract base class for all cmaps.
+  //
+  // CMap equality is based on the equality of the (@link {@link CMapId} that
+  // defines the CMap. In the cmap table for a font there can only be one cmap
+  // with a given cmap id (pair of platform and encoding ids) no matter what the
+  // type of the cmap is.
+  //
+  // The cmap offers CharacterIterator to allow iteration over
+  // characters that are mapped by the cmap. This iteration mostly returns the
+  // characters mapped by the cmap. It will return all characters mapped by the
+  // cmap to anything but .notdef <b>but</b> it may return some that are not
+  // mapped or are mapped to .notdef. Various cmap tables provide ranges and
+  // such to describe characters for lookup but without going the full way to
+  // mapping to the glyph id it isn't always possible to tell if a character
+  // will end up with a valid glyph id. So, some of the characters returned from
+  // the Iterator may still end up pointing to the .notdef glyph. However, the
+  // number of such characters should be small in most cases with well designed
+  // cmaps.
+  class Builder;
+  class CMap : public SubTable {
+   public:
+    // CMapTable::CMap::Builder
+    class Builder : public SubTable::Builder {
+     public:
+      virtual ~Builder();
+
+      CALLER_ATTACH static Builder*
+          GetBuilder(ReadableFontData* data,
+                     int32_t offset,
+                     const CMapId& cmap_id);
+      CALLER_ATTACH static Builder*
+          GetBuilder(int32_t format,
+                     const CMapId& cmap_id);
+
+      // Note: yes, an object is returned on stack since it's small enough.
+      virtual CMapId cmap_id() { return cmap_id_; }
+      virtual int32_t platform_id() { return cmap_id_.platform_id; }
+      virtual int32_t encoding_id() { return cmap_id_.encoding_id; }
+      virtual int32_t format() { return format_; }
+      virtual int32_t language() { return language_; }
+      virtual void set_language(int32_t language) { language_ = language; }
+
+     protected:
+      Builder(ReadableFontData* data,
+              int32_t format,
+              const CMapId& cmap_id);
+      Builder(WritableFontData* data,
+              int32_t format,
+              const CMapId& cmap_id);
+
+      virtual int32_t SubSerialize(WritableFontData* new_data);
+      virtual bool SubReadyToSerialize();
+      virtual int32_t SubDataSizeToSerialize();
+      virtual void SubDataSet();
+
+     private:
+      int32_t format_;
+      CMapId cmap_id_;
+      int32_t language_;
+
+      friend class CMapTable::Builder;
+    };
+    // Abstract CMap character iterator
+    // The fully qualified name is CMapTable::CMap::CharacterIterator
+    class CharacterIterator {
+     public:
+      virtual ~CharacterIterator() {}
+      virtual bool HasNext() = 0;
+      // Returns -1 if there are no more characters to iterate through
+      // and exceptions are turned off
+      virtual int32_t Next() = 0;
+
+     protected:
+      // Use the CMap::Iterator method below instead of directly requesting
+      // a CharacterIterator.
+      CharacterIterator() {}
+    };
+
+    CMap(ReadableFontData* data, int32_t format, const CMapId& cmap_id);
+    virtual ~CMap();
+
+    virtual CMap::CharacterIterator* Iterator() = 0;
+
+    virtual int32_t format() { return format_; }
+    virtual CMapId cmap_id() { return cmap_id_; }
+    virtual int32_t platform_id() { return cmap_id_.platform_id; }
+    virtual int32_t encoding_id() { return cmap_id_.encoding_id; }
+
+    // Get the language of the cmap.
+    //
+    // Note on the language field in 'cmap' subtables: The language field must
+    // be set to zero for all cmap subtables whose platform IDs are other than
+    // Macintosh (platform ID 1). For cmap subtables whose platform IDs are
+    // Macintosh, set this field to the Macintosh language ID of the cmap
+    // subtable plus one, or to zero if the cmap subtable is not
+    // language-specific. For example, a Mac OS Turkish cmap subtable must set
+    // this field to 18, since the Macintosh language ID for Turkish is 17. A
+    // Mac OS Roman cmap subtable must set this field to 0, since Mac OS Roman
+    // is not a language-specific encoding.
+    //
+    // @return the language id
+    virtual int32_t Language() = 0;
+
+    // Gets the glyph id for the character code provided.
+    // The character code provided must be in the encoding used by the cmap
+    // table.
+    virtual int32_t GlyphId(int32_t character) = 0;
+
+   private:
+    int32_t format_;
+    CMapId cmap_id_;
+  };
+  typedef Ptr<CMap> CMapPtr;
+  typedef Ptr<CMap::Builder> CMapBuilderPtr;
+  typedef std::map<CMapId, CMapBuilderPtr, CMapIdComparator> CMapBuilderMap;
+
+  // A cmap format 0 sub table
+  class CMapFormat0 : public CMap, public RefCounted<CMapFormat0> {
+   public:
+    // The fully qualified name is CMapTable::CMapFormat0::Builder
+    class Builder : public CMap::Builder,
+                    public RefCounted<Builder> {
+     public:
+      CALLER_ATTACH static Builder* NewInstance(ReadableFontData* data,
+                                                int32_t offset,
+                                                const CMapId& cmap_id);
+      CALLER_ATTACH static Builder* NewInstance(WritableFontData* data,
+                                                int32_t offset,
+                                                const CMapId& cmap_id);
+      CALLER_ATTACH static Builder* NewInstance(const CMapId& cmap_id);
+      virtual ~Builder();
+
+     protected:
+      virtual CALLER_ATTACH FontDataTable*
+          SubBuildTable(ReadableFontData* data);
+
+     private:
+      // When creating a new CMapFormat0 Builder, use NewInstance instead of
+      // the constructors! This avoids a memory leak when slicing the FontData.
+      Builder(ReadableFontData* data, int32_t offset, const CMapId& cmap_id);
+      Builder(WritableFontData* data, int32_t offset, const CMapId& cmap_id);
+      Builder(const CMapId& cmap_id);
+    };
+
+    // The fully qualified name is CMapTable::CMapFormat0::CharacterIterator
+    class CharacterIterator : public CMap::CharacterIterator {
+     public:
+      virtual ~CharacterIterator();
+      virtual bool HasNext();
+      virtual int32_t Next();
+
+     private:
+      CharacterIterator(int32_t start, int32_t end);
+      friend class CMapFormat0;
+      int32_t character_, max_character_;
+    };
+
+    virtual ~CMapFormat0();
+    virtual int32_t Language();
+    virtual int32_t GlyphId(int32_t character);
+    CMap::CharacterIterator* Iterator();
+
+   private:
+    CMapFormat0(ReadableFontData* data, const CMapId& cmap_id);
+  };
+
+  // A cmap format 2 sub table
+  // The format 2 cmap is used for multi-byte encodings such as SJIS,
+  // EUC-JP/KR/CN, Big5, etc.
+  class CMapFormat2 : public CMap, public RefCounted<CMapFormat2> {
+   public:
+    // CMapTable::CMapFormat2::Builder
+    class Builder : public CMap::Builder,
+                    public RefCounted<Builder> {
+     public:
+      Builder(ReadableFontData* data,
+              int32_t offset,
+              const CMapId& cmap_id);
+      Builder(WritableFontData* data,
+              int32_t offset,
+              const CMapId& cmap_id);
+      virtual ~Builder();
+
+     protected:
+      virtual CALLER_ATTACH FontDataTable*
+          SubBuildTable(ReadableFontData* data);
+    };
+    // CMapTable::CMapFormat2::CharacterIterator
+    class CharacterIterator : public CMap::CharacterIterator {
+     public:
+      virtual ~CharacterIterator();
+      virtual bool hasNext();
+      virtual int32_t next();
+
+     private:
+      CharacterIterator();
+    };
+
+    virtual int32_t Language();
+    virtual int32_t GlyphId(int32_t character);
+
+    // Returns how many bytes would be consumed by a lookup of this character
+    // with this cmap. This comes about because the cmap format 2 table is
+    // designed around multi-byte encodings such as SJIS, EUC-JP, Big5, etc.
+    // return the number of bytes consumed from this "character" - either 1 or 2
+    virtual int32_t BytesConsumed(int32_t character);
+
+    virtual ~CMapFormat2();
+
+   private:
+    CMapFormat2(ReadableFontData* data, const CMapId& cmap_id);
+
+    int32_t SubHeaderOffset(int32_t sub_header_index);
+    int32_t FirstCode(int32_t sub_header_index);
+    int32_t EntryCount(int32_t sub_header_index);
+    int32_t IdRangeOffset(int32_t sub_header_index);
+    int32_t IdDelta(int32_t sub_header_index);
+    CMap::CharacterIterator* Iterator();
+  };
+
+    // CMapTable::CMapFormat4
+  class CMapFormat4 : public CMap,
+                      public RefCounted<CMapFormat4> {
+   public:
+    // CMapTable::CMapFormat4::Builder
+    class Builder : public CMap::Builder,
+                    public RefCounted<Builder> {
+     public:
+        // CMapTable::CMapFormat4::Builder::Segment
+      class Segment : public RefCounted<Segment> {
+       public:
+        Segment();
+        explicit Segment(Segment* other);
+        Segment(int32_t start_count,
+                int32_t end_count,
+                int32_t id_delta,
+                int32_t id_range_offset);
+        ~Segment();
+
+        // @return the startCount
+        int32_t start_count();
+        // @param startCount the startCount to set
+        void set_start_count(int32_t start_count);
+        // @return the endCount
+        int32_t end_count();
+        // @param endcount the endCount to set
+        void set_end_count(int32_t end_count);
+        // @return the idDelta
+        int32_t id_delta();
+        // @param idDelta the idDelta to set
+        void set_id_delta(int32_t id_delta);
+        // @return the idRangeOffset
+        int32_t id_range_offset();
+        // @param idRangeOffset the idRangeOffset to set
+        void set_id_range_offset(int32_t id_range_offset);
+
+        static CALLER_ATTACH
+        std::vector<Ptr<Segment> >*
+        DeepCopy(std::vector<Ptr<Segment> >* original);
+
+       private:
+        int32_t start_count_;
+        int32_t end_count_;
+        int32_t id_delta_;
+        int32_t id_range_offset_;
+      };
+      typedef std::vector<Ptr<Segment> > SegmentList;
+
+      static CALLER_ATTACH Builder* NewInstance(WritableFontData* data,
+                                                int32_t offset,
+                                                const CMapId& cmap_id);
+      static CALLER_ATTACH Builder* NewInstance(ReadableFontData* data,
+                                                int32_t offset,
+                                                const CMapId& cmap_id);
+      static CALLER_ATTACH Builder* NewInstance(const CMapId& cmap_id);
+      virtual ~Builder();
+      SegmentList* segments();
+      void set_segments(SegmentList* segments);
+      IntegerList* glyph_id_array();
+      void set_glyph_id_array(IntegerList* glyph_id_array);
+
+     protected:
+      Builder(WritableFontData* data, int32_t offset, const CMapId& cmap_id);
+      Builder(ReadableFontData* data, int32_t offset, const CMapId& cmap_id);
+      Builder(SegmentList* segments, IntegerList* glyph_id_array,
+              const CMapId& cmap_id);
+      explicit Builder(const CMapId& cmap_id);
+
+      virtual CALLER_ATTACH FontDataTable* SubBuildTable(
+          ReadableFontData* data);
+      virtual void SubDataSet();
+      virtual int32_t SubDataSizeToSerialize();
+      virtual bool SubReadyToSerialize();
+      virtual int32_t SubSerialize(WritableFontData* new_data);
+
+     private:
+      void Initialize(ReadableFontData* data);
+
+      SegmentList segments_;
+      IntegerList glyph_id_array_;
+    };
+
+    CMap::CharacterIterator* Iterator();
+    // CMapTable::CMapFormat4::CharacterIterator
+    class CharacterIterator : public CMap::CharacterIterator {
+     public:
+      bool HasNext();
+      int32_t Next();
+      virtual ~CharacterIterator() {}
+
+     private:
+      explicit CharacterIterator(CMapFormat4 *parent);
+      friend CMap::CharacterIterator* CMapFormat4::Iterator();
+
+      CMapFormat4* parent_;
+      int32_t segment_index_;
+      int32_t first_char_in_segment_;
+      int32_t last_char_in_segment_;
+      int32_t next_char_;
+      bool next_char_set_;
+    };
+
+    virtual int32_t GlyphId(int32_t character);
+
+    // Lower level glyph code retrieval that requires processing the Format 4
+    // segments to use.
+    // @param segment the cmap segment
+    // @param startCode the start code for the segment
+    // @param character the character to be looked up
+    // @return the glyph id for the character; CMapTable.NOTDEF if not found
+    int32_t RetrieveGlyphId(int32_t segment,
+                            int32_t start_count,
+                            int32_t character);
+    virtual int32_t Language();
+
+    // Get the count of the number of segments in this cmap.
+    // @return the number of segments
+    int32_t seg_count();
+    int32_t Length();
+    // Get the start code for a segment.
+    // @param segment the segment in the lookup table
+    // @return the start code for a segment
+    int32_t StartCode(int32_t segment);
+    // Get the end code for a segment.
+    // @param segment the segment in the look up table
+    // @return the end code for the segment
+    int32_t EndCode(int32_t segment);
+    // Get the id delta for a segment
+    // @param segment the segment in the look up table
+    // @return the id delta for the segment
+    int32_t IdDelta(int32_t segment);
+    // Get the id range offset for a segment
+    // @param segment the segment in the look up table
+    // @return the id range offset for the segment
+    int32_t IdRangeOffset(int32_t segment);
+    // Get the location of the id range offset for a segment
+    // @param segment the segment in the look up table
+    // @return the location of the id range offset for the segment
+    int32_t IdRangeOffsetLocation(int32_t segment);
+    // Declared above to allow friending inside CharacterIterator class.
+    // CMap::CharacterIterator* Iterator();
+    virtual ~CMapFormat4();
+
+   protected:
+    CMapFormat4(ReadableFontData* data, const CMapId& cmap_id);
+
+   private:
+    static int32_t Language(ReadableFontData* data);
+    static int32_t Length(ReadableFontData* data);
+    static int32_t SegCount(ReadableFontData* data);
+    static int32_t StartCode(ReadableFontData* data,
+                             int32_t seg_count,
+                             int32_t index);
+    static int32_t StartCodeOffset(int32_t seg_count);
+    static int32_t EndCode(ReadableFontData* data,
+                           int32_t seg_count,
+                           int32_t index);
+    static int32_t IdDelta(ReadableFontData* data,
+                           int32_t seg_count,
+                           int32_t index);
+    static int32_t IdDeltaOffset(int32_t seg_count);
+    static int32_t IdRangeOffset(ReadableFontData* data,
+                                 int32_t seg_count,
+                                 int32_t index);
+    static int32_t IdRangeOffsetOffset(int32_t seg_count);
+    static int32_t GlyphIdArrayOffset(int32_t seg_count);
+    // Refactored void to bool to work without exceptions.
+    bool IsValidIndex(int32_t segment);
+    int32_t GlyphIdArray(int32_t index);
+
+    int32_t seg_count_;
+    int32_t start_code_offset_;
+    int32_t id_delta_offset_;
+    int32_t glyph_id_array_offset_;
+  };
+
+  // CMapTable::Builder
+  class Builder : public SubTableContainerTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    // Constructor scope is public because C++ does not allow base class to
+    // instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual void SubDataSet();
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    CMap::Builder* NewCMapBuilder(const CMapId& cmap_id,
+                                  ReadableFontData* data);
+    // Create a new empty CMapBuilder of the type specified in the id.
+    CMap::Builder* NewCMapBuilder(int32_t format, const CMapId& cmap_id);
+    CMap::Builder* CMapBuilder(const CMapId& cmap_id);
+
+    int32_t NumCMaps();
+    void SetVersion(int32_t version);
+
+    CMapBuilderMap* GetCMapBuilders();
+
+   protected:
+    static CALLER_ATTACH CMap::Builder* CMapBuilder(ReadableFontData* data,
+                                                    int32_t index);
+
+   private:
+    void Initialize(ReadableFontData* data);
+    static int32_t NumCMaps(ReadableFontData* data);
+
+    int32_t version_;
+    CMapBuilderMap cmap_builders_;
+  };
+  typedef Ptr<Builder> CMapTableBuilderPtr;
+
+  class CMapIterator {
+   public:
+    // If filter is NULL, filter through all tables.
+    CMapIterator(CMapTable* table, const CMapFilter* filter);
+    bool HasNext();
+    CMap* Next();
+
+   private:
+    int32_t table_index_;
+    const CMapFilter* filter_;
+    CMapTable* table_;
+  };
+
+  // Make a CMapId from a platform_id, encoding_id pair
+  static CMapId NewCMapId(int32_t platform_id, int32_t encoding_id);
+  // Make a CMapId from another CMapId
+  static CMapId NewCMapId(const CMapId& obj);
+
+  // Get the CMap with the specified parameters if it exists.
+  // Returns NULL otherwise.
+  CALLER_ATTACH CMap* GetCMap(const int32_t index);
+  CALLER_ATTACH CMap* GetCMap(const int32_t platform_id,
+                              const int32_t encoding_id);
+  CALLER_ATTACH CMap* GetCMap(const CMapId GetCMap_id);
+
+  // Get the table version.
+  virtual int32_t Version();
+
+  // Get the number of cmaps within the CMap table.
+  virtual int32_t NumCMaps();
+
+  // Get the cmap id for the cmap with the given index.
+  // Note: yes, an object is returned on stack since it's small enough.
+  //       This function is renamed from cmapId to GetCMapId().
+  virtual CMapId GetCMapId(int32_t index);
+
+  virtual int32_t PlatformId(int32_t index);
+  virtual int32_t EncodingId(int32_t index);
+
+  // Get the offset in the table data for the cmap table with the given index.
+  // The offset is from the beginning of the table.
+  virtual int32_t Offset(int32_t index);
+
+  virtual ~CMapTable();
+
+  static const int32_t NOTDEF;
+
+ private:
+  // Offsets to specific elements in the underlying data. These offsets are
+  // relative to the start of the table or the start of sub-blocks within
+  // the table.
+  struct Offset {
+    enum {
+      kVersion = 0,
+      kNumTables = 2,
+      kEncodingRecordStart = 4,
+
+      // offsets relative to the encoding record
+      kEncodingRecordPlatformId = 0,
+      kEncodingRecordEncodingId = 2,
+      kEncodingRecordOffset = 4,
+      kEncodingRecordSize = 8,
+
+      kFormat = 0,
+
+      // Format 0: Byte encoding table
+      kFormat0Format = 0,
+      kFormat0Length = 2,
+      kFormat0Language = 4,
+      kFormat0GlyphIdArray = 6,
+
+      // Format 2: High-byte mapping through table
+      kFormat2Format = 0,
+      kFormat2Length = 2,
+      kFormat2Language = 4,
+      kFormat2SubHeaderKeys = 6,
+      kFormat2SubHeaders = 518,
+      // offset relative to the subHeader structure
+      kFormat2SubHeader_firstCode = 0,
+      kFormat2SubHeader_entryCount = 2,
+      kFormat2SubHeader_idDelta = 4,
+      kFormat2SubHeader_idRangeOffset = 6,
+      kFormat2SubHeader_structLength = 8,
+
+      // Format 4: Segment mapping to delta values
+      kFormat4Format = 0,
+      kFormat4Length = 2,
+      kFormat4Language = 4,
+      kFormat4SegCountX2 = 6,
+      kFormat4SearchRange = 8,
+      kFormat4EntrySelector = 10,
+      kFormat4RangeShift = 12,
+      kFormat4EndCount = 14,
+      kFormat4FixedSize = 16,
+
+      // format 6: Trimmed table mapping
+      kFormat6Format = 0,
+      kFormat6Length = 2,
+      kFormat6Language = 4,
+      kFormat6FirstCode = 6,
+      kFormat6EntryCount = 8,
+      kFormat6GlyphIdArray = 10,
+
+      // Format 8: mixed 16-bit and 32-bit coverage
+      kFormat8Format = 0,
+      kFormat8Length = 4,
+      kFormat8Language = 8,
+      kFormat8Is32 = 12,
+      kFormat8nGroups204 = 8204,
+      kFormat8Groups208 = 8208,
+      // offset relative to the group structure
+      kFormat8Group_startCharCode = 0,
+      kFormat8Group_endCharCode = 4,
+      kFormat8Group_startGlyphId = 8,
+      kFormat8Group_structLength = 12,
+
+      // Format 10: Trimmed array
+      kFormat10Format = 0,
+      kFormat10Length = 4,
+      kFormat10Language = 8,
+      kFormat10StartCharCode = 12,
+      kFormat10NumChars = 16,
+      kFormat10Glyphs0 = 20,
+
+      // Format 12: Segmented coverage
+      kFormat12Format = 0,
+      kFormat12Length = 4,
+      kFormat12Language = 8,
+      kFormat12nGroups = 12,
+      kFormat12Groups = 16,
+      kFormat12Groups_structLength = 12,
+      // offsets within the group structure
+      kFormat12_startCharCode = 0,
+      kFormat12_endCharCode = 4,
+      kFormat12_startGlyphId = 8,
+
+      // Format 13: Last Resort Font
+      kFormat13Format = 0,
+      kFormat13Length = 4,
+      kFormat13Language = 8,
+      kFormat13nGroups = 12,
+      kFormat13Groups = 16,
+      kFormat13Groups_structLength = 12,
+      // offsets within the group structure
+      kFormat13_startCharCode = 0,
+      kFormat13_endCharCode = 4,
+      kFormat13_glyphId = 8,
+
+      // Format 14: Unicode Variation Sequences
+      kFormat14Format = 0,
+      kFormat14Length = 2,
+
+      // TODO(stuartg): finish tables
+      // Default UVS Table
+
+      // Non-default UVS Table
+      kLast = -1
+    };
+  };
+
+  CMapTable(Header* header, ReadableFontData* data);
+
+  // Get the offset in the table data for the encoding record for the cmap with
+  // the given index. The offset is from the beginning of the table.
+  static int32_t OffsetForEncodingRecord(int32_t index);
+};
+typedef std::vector<CMapTable::CMapId> CMapIdList;
+typedef Ptr<CMapTable> CMapTablePtr;
+typedef std::vector<Ptr<CMapTable::CMapFormat4::Builder::Segment> > SegmentList;
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_CMAP_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/font_header_table.cc b/sfntly/cpp/src/sfntly/table/core/font_header_table.cc
new file mode 100644
index 0000000..60015ca
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/font_header_table.cc
@@ -0,0 +1,265 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/core/font_header_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * FontHeaderTable class
+ ******************************************************************************/
+FontHeaderTable::~FontHeaderTable() {}
+
+int32_t FontHeaderTable::TableVersion() {
+  return data_->ReadFixed(Offset::kTableVersion);
+}
+
+int32_t FontHeaderTable::FontRevision() {
+  return data_->ReadFixed(Offset::kFontRevision);
+}
+
+int64_t FontHeaderTable::ChecksumAdjustment() {
+  return data_->ReadULong(Offset::kCheckSumAdjustment);
+}
+
+int64_t FontHeaderTable::MagicNumber() {
+  return data_->ReadULong(Offset::kMagicNumber);
+}
+
+int32_t FontHeaderTable::FlagsAsInt() {
+  return data_->ReadUShort(Offset::kFlags);
+}
+
+int32_t FontHeaderTable::UnitsPerEm() {
+  return data_->ReadUShort(Offset::kUnitsPerEm);
+}
+
+int64_t FontHeaderTable::Created() {
+  return data_->ReadDateTimeAsLong(Offset::kCreated);
+}
+
+int64_t FontHeaderTable::Modified() {
+  return data_->ReadDateTimeAsLong(Offset::kModified);
+}
+
+int32_t FontHeaderTable::XMin() {
+  return data_->ReadUShort(Offset::kXMin);
+}
+
+int32_t FontHeaderTable::YMin() {
+  return data_->ReadUShort(Offset::kYMin);
+}
+
+int32_t FontHeaderTable::XMax() {
+  return data_->ReadUShort(Offset::kXMax);
+}
+
+int32_t FontHeaderTable::YMax() {
+  return data_->ReadUShort(Offset::kYMax);
+}
+
+int32_t FontHeaderTable::MacStyleAsInt() {
+  return data_->ReadUShort(Offset::kMacStyle);
+}
+
+int32_t FontHeaderTable::LowestRecPPEM() {
+  return data_->ReadUShort(Offset::kLowestRecPPEM);
+}
+
+int32_t FontHeaderTable::FontDirectionHint() {
+  return data_->ReadShort(Offset::kFontDirectionHint);
+}
+
+int32_t FontHeaderTable::IndexToLocFormat() {
+  return data_->ReadShort(Offset::kIndexToLocFormat);
+}
+
+int32_t FontHeaderTable::GlyphDataFormat() {
+  return data_->ReadShort(Offset::kGlyphDataFormat);
+}
+
+FontHeaderTable::FontHeaderTable(Header* header, ReadableFontData* data)
+    : Table(header, data) {
+  IntegerList checksum_ranges;
+  checksum_ranges.push_back(0);
+  checksum_ranges.push_back(Offset::kCheckSumAdjustment);
+  checksum_ranges.push_back(Offset::kMagicNumber);
+  data_->SetCheckSumRanges(checksum_ranges);
+}
+
+/******************************************************************************
+ * FontHeaderTable::Builder class
+ ******************************************************************************/
+FontHeaderTable::Builder::Builder(Header* header, WritableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+FontHeaderTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+FontHeaderTable::Builder::~Builder() {}
+
+CALLER_ATTACH FontDataTable* FontHeaderTable::Builder::SubBuildTable(
+    ReadableFontData* data) {
+  FontDataTablePtr table = new FontHeaderTable(header(), data);
+  return table.Detach();
+}
+
+int32_t FontHeaderTable::Builder::TableVersion() {
+  return down_cast<FontHeaderTable*>(GetTable())->TableVersion();
+}
+
+void FontHeaderTable::Builder::SetTableVersion(int32_t version) {
+  InternalWriteData()->WriteFixed(Offset::kTableVersion, version);
+}
+
+int32_t FontHeaderTable::Builder::FontRevision() {
+  return down_cast<FontHeaderTable*>(GetTable())->FontRevision();
+}
+
+void FontHeaderTable::Builder::SetFontRevision(int32_t revision) {
+  InternalWriteData()->WriteFixed(Offset::kFontRevision, revision);
+}
+
+int64_t FontHeaderTable::Builder::ChecksumAdjustment() {
+  return down_cast<FontHeaderTable*>(GetTable())->ChecksumAdjustment();
+}
+
+void FontHeaderTable::Builder::SetChecksumAdjustment(int64_t adjustment) {
+  InternalWriteData()->WriteULong(Offset::kCheckSumAdjustment, adjustment);
+}
+
+int64_t FontHeaderTable::Builder::MagicNumber() {
+  return down_cast<FontHeaderTable*>(GetTable())->MagicNumber();
+}
+
+void FontHeaderTable::Builder::SetMagicNumber(int64_t magic_number) {
+  InternalWriteData()->WriteULong(Offset::kMagicNumber, magic_number);
+}
+
+int32_t FontHeaderTable::Builder::FlagsAsInt() {
+  return down_cast<FontHeaderTable*>(GetTable())->FlagsAsInt();
+}
+
+void FontHeaderTable::Builder::SetFlagsAsInt(int32_t flags) {
+  InternalWriteData()->WriteUShort(Offset::kFlags, flags);
+}
+
+int32_t FontHeaderTable::Builder::UnitsPerEm() {
+  return down_cast<FontHeaderTable*>(GetTable())->UnitsPerEm();
+}
+
+void FontHeaderTable::Builder::SetUnitsPerEm(int32_t units) {
+  InternalWriteData()->WriteUShort(Offset::kUnitsPerEm, units);
+}
+
+int64_t FontHeaderTable::Builder::Created() {
+  return down_cast<FontHeaderTable*>(GetTable())->Created();
+}
+
+void FontHeaderTable::Builder::SetCreated(int64_t date) {
+  InternalWriteData()->WriteDateTime(Offset::kCreated, date);
+}
+
+int64_t FontHeaderTable::Builder::Modified() {
+  return down_cast<FontHeaderTable*>(GetTable())->Modified();
+}
+
+void FontHeaderTable::Builder::SetModified(int64_t date) {
+  InternalWriteData()->WriteDateTime(Offset::kModified, date);
+}
+
+int32_t FontHeaderTable::Builder::XMin() {
+  return down_cast<FontHeaderTable*>(GetTable())->XMin();
+}
+
+void FontHeaderTable::Builder::SetXMin(int32_t xmin) {
+  InternalWriteData()->WriteShort(Offset::kXMin, xmin);
+}
+
+int32_t FontHeaderTable::Builder::YMin() {
+  return down_cast<FontHeaderTable*>(GetTable())->YMin();
+}
+
+void FontHeaderTable::Builder::SetYMin(int32_t ymin) {
+  InternalWriteData()->WriteShort(Offset::kYMin, ymin);
+}
+
+int32_t FontHeaderTable::Builder::XMax() {
+  return down_cast<FontHeaderTable*>(GetTable())->XMax();
+}
+
+void FontHeaderTable::Builder::SetXMax(int32_t xmax) {
+  InternalWriteData()->WriteShort(Offset::kXMax, xmax);
+}
+
+int32_t FontHeaderTable::Builder::YMax() {
+  return down_cast<FontHeaderTable*>(GetTable())->YMax();
+}
+
+void FontHeaderTable::Builder::SetYMax(int32_t ymax) {
+  InternalWriteData()->WriteShort(Offset::kYMax, ymax);
+}
+
+int32_t FontHeaderTable::Builder::MacStyleAsInt() {
+  return down_cast<FontHeaderTable*>(GetTable())->MacStyleAsInt();
+}
+
+void FontHeaderTable::Builder::SetMacStyleAsInt(int32_t style) {
+  InternalWriteData()->WriteUShort(Offset::kMacStyle, style);
+}
+
+int32_t FontHeaderTable::Builder::LowestRecPPEM() {
+  return down_cast<FontHeaderTable*>(GetTable())->LowestRecPPEM();
+}
+
+void FontHeaderTable::Builder::SetLowestRecPPEM(int32_t size) {
+  InternalWriteData()->WriteUShort(Offset::kLowestRecPPEM, size);
+}
+
+int32_t FontHeaderTable::Builder::FontDirectionHint() {
+  return down_cast<FontHeaderTable*>(GetTable())->FontDirectionHint();
+}
+
+void FontHeaderTable::Builder::SetFontDirectionHint(int32_t hint) {
+  InternalWriteData()->WriteShort(Offset::kFontDirectionHint, hint);
+}
+
+int32_t FontHeaderTable::Builder::IndexToLocFormat() {
+  return down_cast<FontHeaderTable*>(GetTable())->IndexToLocFormat();
+}
+
+void FontHeaderTable::Builder::SetIndexToLocFormat(int32_t format) {
+  InternalWriteData()->WriteShort(Offset::kIndexToLocFormat, format);
+}
+
+int32_t FontHeaderTable::Builder::GlyphDataFormat() {
+  return down_cast<FontHeaderTable*>(GetTable())->GlyphDataFormat();
+}
+
+void FontHeaderTable::Builder::SetGlyphDataFormat(int32_t format) {
+  InternalWriteData()->WriteShort(Offset::kGlyphDataFormat, format);
+}
+
+CALLER_ATTACH FontHeaderTable::Builder*
+    FontHeaderTable::Builder::CreateBuilder(Header* header,
+                                            WritableFontData* data) {
+  Ptr<FontHeaderTable::Builder> builder;
+  builder = new FontHeaderTable::Builder(header, data);
+  return builder.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/font_header_table.h b/sfntly/cpp/src/sfntly/table/core/font_header_table.h
new file mode 100644
index 0000000..841955b
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/font_header_table.h
@@ -0,0 +1,168 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_FONT_HEADER_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_FONT_HEADER_TABLE_H_
+
+#include "sfntly/table/table.h"
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+struct IndexToLocFormat {
+  enum {
+    kShortOffset = 0,
+    kLongOffset = 1
+  };
+};
+
+struct FontDirectionHint {
+  enum {
+    kFullyMixed = 0,
+    kOnlyStrongLTR = 1,
+    kStrongLTRAndNeutral = 2,
+    kOnlyStrongRTL = -1,
+    kStrongRTLAndNeutral = -2
+  };
+};
+
+class FontHeaderTable : public Table, public RefCounted<FontHeaderTable> {
+ public:
+  class Builder : public TableBasedTableBuilder, public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+    virtual int32_t TableVersion();
+    virtual void SetTableVersion(int32_t version);
+    virtual int32_t FontRevision();
+    virtual void SetFontRevision(int32_t revision);
+    virtual int64_t ChecksumAdjustment();
+    virtual void SetChecksumAdjustment(int64_t adjustment);
+    virtual int64_t MagicNumber();
+    virtual void SetMagicNumber(int64_t magic_number);
+    virtual int32_t FlagsAsInt();
+    virtual void SetFlagsAsInt(int32_t flags);
+    // TODO(arthurhsu): IMPLEMENT EnumSet<Flags> Flags()
+    // TODO(arthurhsu): IMPLEMENT setFlags(EnumSet<Flags> flags)
+    virtual int32_t UnitsPerEm();
+    virtual void SetUnitsPerEm(int32_t units);
+    virtual int64_t Created();
+    virtual void SetCreated(int64_t date);
+    virtual int64_t Modified();
+    virtual void SetModified(int64_t date);
+    virtual int32_t XMin();
+    virtual void SetXMin(int32_t xmin);
+    virtual int32_t YMin();
+    virtual void SetYMin(int32_t ymin);
+    virtual int32_t XMax();
+    virtual void SetXMax(int32_t xmax);
+    virtual int32_t YMax();
+    virtual void SetYMax(int32_t ymax);
+    virtual int32_t MacStyleAsInt();
+    virtual void SetMacStyleAsInt(int32_t style);
+    // TODO(arthurhsu): IMPLEMENT EnumSet<MacStyle> macStyle()
+    // TODO(arthurhsu): IMPLEMENT setMacStyle(EnumSet<MacStyle> style)
+    virtual int32_t LowestRecPPEM();
+    virtual void SetLowestRecPPEM(int32_t size);
+    virtual int32_t FontDirectionHint();
+    virtual void SetFontDirectionHint(int32_t hint);
+    virtual int32_t IndexToLocFormat();
+    virtual void SetIndexToLocFormat(int32_t format);
+    virtual int32_t GlyphDataFormat();
+    virtual void SetGlyphDataFormat(int32_t format);
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+  };
+
+  virtual ~FontHeaderTable();
+  int32_t TableVersion();
+  int32_t FontRevision();
+
+  // Get the checksum adjustment. To compute: set it to 0, sum the entire font
+  // as ULONG, then store 0xB1B0AFBA - sum.
+  int64_t ChecksumAdjustment();
+
+  // Get the magic number. Set to 0x5F0F3CF5.
+  int64_t MagicNumber();
+
+  // TODO(arthurhsu): IMPLEMENT: EnumSet<Flags>
+  int32_t FlagsAsInt();
+  // TODO(arthurhsu): IMPLEMENT: Flags() returning EnumSet<Flags>
+
+  int32_t UnitsPerEm();
+
+  // Get the created date. Number of seconds since 12:00 midnight, January 1,
+  // 1904. 64-bit integer.
+  int64_t Created();
+  // Get the modified date. Number of seconds since 12:00 midnight, January 1,
+  // 1904. 64-bit integer.
+  int64_t Modified();
+
+  // Get the x min. For all glyph bounding boxes.
+  int32_t XMin();
+  // Get the y min. For all glyph bounding boxes.
+  int32_t YMin();
+  // Get the x max. For all glyph bounding boxes.
+  int32_t XMax();
+  // Get the y max. For all glyph bounding boxes.
+  int32_t YMax();
+
+  // TODO(arthurhsu): IMPLEMENT: EnumSet<MacStyle>
+  int32_t MacStyleAsInt();
+  // TODO(arthurhsu): IMPLEMENT: macStyle() returning EnumSet<MacStyle>
+
+  int32_t LowestRecPPEM();
+  int32_t FontDirectionHint();  // Note: no AsInt() form, already int
+  int32_t IndexToLocFormat();  // Note: no AsInt() form, already int
+  int32_t GlyphDataFormat();
+
+ private:
+  struct Offset {
+    enum {
+      kTableVersion = 0,
+      kFontRevision = 4,
+      kCheckSumAdjustment = 8,
+      kMagicNumber = 12,
+      kFlags = 16,
+      kUnitsPerEm = 18,
+      kCreated = 20,
+      kModified = 28,
+      kXMin = 36,
+      kYMin = 38,
+      kXMax = 40,
+      kYMax = 42,
+      kMacStyle = 44,
+      kLowestRecPPEM = 46,
+      kFontDirectionHint = 48,
+      kIndexToLocFormat = 50,
+      kGlyphDataFormat = 52
+    };
+  };
+
+  FontHeaderTable(Header* header, ReadableFontData* data);
+};
+typedef Ptr<FontHeaderTable> FontHeaderTablePtr;
+typedef Ptr<FontHeaderTable::Builder> FontHeaderTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_FONT_HEADER_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/horizontal_device_metrics_table.cc b/sfntly/cpp/src/sfntly/table/core/horizontal_device_metrics_table.cc
new file mode 100644
index 0000000..50b0cf5
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/horizontal_device_metrics_table.cc
@@ -0,0 +1,124 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/core/horizontal_device_metrics_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * HorizontalDeviceMetricsTable class
+ ******************************************************************************/
+HorizontalDeviceMetricsTable:: ~HorizontalDeviceMetricsTable() {}
+
+int32_t HorizontalDeviceMetricsTable::Version() {
+  return data_->ReadUShort(Offset::kVersion);
+}
+
+int32_t HorizontalDeviceMetricsTable::NumRecords() {
+  return data_->ReadShort(Offset::kNumRecords);
+}
+
+int32_t HorizontalDeviceMetricsTable::RecordSize() {
+  return data_->ReadLong(Offset::kSizeDeviceRecord);
+}
+
+int32_t HorizontalDeviceMetricsTable::PixelSize(int32_t record_index) {
+  if (record_index < 0 || record_index >= NumRecords()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException();
+#endif
+    return -1;
+  }
+  return data_->ReadUByte(Offset::kRecords + record_index * RecordSize() +
+                          Offset::kDeviceRecordPixelSize);
+}
+
+int32_t HorizontalDeviceMetricsTable::MaxWidth(int32_t record_index) {
+  if (record_index < 0 || record_index >= NumRecords()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException();
+#endif
+    return -1;
+  }
+  return data_->ReadUByte(Offset::kRecords + record_index * RecordSize() +
+                          Offset::kDeviceRecordMaxWidth);
+}
+
+int32_t HorizontalDeviceMetricsTable::Width(int32_t record_index,
+                                            int32_t glyph_num) {
+  if (record_index < 0 || record_index >= NumRecords() ||
+      glyph_num < 0 || glyph_num >= num_glyphs_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException();
+#endif
+    return -1;
+  }
+  return data_->ReadUByte(Offset::kRecords + record_index * RecordSize() +
+                          Offset::kDeviceRecordWidths + glyph_num);
+}
+
+HorizontalDeviceMetricsTable::HorizontalDeviceMetricsTable(
+    Header* header,
+    ReadableFontData* data,
+    int32_t num_glyphs)
+    : Table(header, data), num_glyphs_(num_glyphs) {
+}
+
+/******************************************************************************
+ * HorizontalDeviceMetricsTable::Builder class
+ ******************************************************************************/
+HorizontalDeviceMetricsTable::Builder::Builder(Header* header,
+                                               WritableFontData* data)
+    : TableBasedTableBuilder(header, data), num_glyphs_(-1) {
+}
+
+HorizontalDeviceMetricsTable::Builder::Builder(Header* header,
+                                               ReadableFontData* data)
+    : TableBasedTableBuilder(header, data), num_glyphs_(-1) {
+}
+
+HorizontalDeviceMetricsTable::Builder::~Builder() {}
+
+CALLER_ATTACH FontDataTable*
+HorizontalDeviceMetricsTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new HorizontalDeviceMetricsTable(header(), data,
+                                                            num_glyphs_);
+  return table.Detach();
+}
+
+void HorizontalDeviceMetricsTable::Builder::SetNumGlyphs(int32_t num_glyphs) {
+  if (num_glyphs < 0) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IllegalArgumentException("Number of glyphs can't be negative.");
+#endif
+    return;
+  }
+  num_glyphs_ = num_glyphs;
+  HorizontalDeviceMetricsTable* table =
+      down_cast<HorizontalDeviceMetricsTable*>(GetTable());
+  if (table) {
+    table->num_glyphs_ = num_glyphs;
+  }
+}
+
+CALLER_ATTACH HorizontalDeviceMetricsTable::Builder*
+HorizontalDeviceMetricsTable::Builder::CreateBuilder(Header* header,
+                                                     WritableFontData* data) {
+  Ptr<HorizontalDeviceMetricsTable::Builder> builder;
+  builder = new HorizontalDeviceMetricsTable::Builder(header, data);
+  return builder.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/horizontal_device_metrics_table.h b/sfntly/cpp/src/sfntly/table/core/horizontal_device_metrics_table.h
new file mode 100644
index 0000000..4a27ba0
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/horizontal_device_metrics_table.h
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_DEVICE_METRICS_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_DEVICE_METRICS_TABLE_H_
+
+#include "sfntly/table/table.h"
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+// A Horizontal Device Metrics table - 'hdmx'
+class HorizontalDeviceMetricsTable
+    : public Table,
+      public RefCounted<HorizontalDeviceMetricsTable> {
+ public:
+  class Builder : public TableBasedTableBuilder, public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    void SetNumGlyphs(int32_t num_glyphs);
+
+   private:
+    int32_t num_glyphs_;
+  };
+
+  virtual ~HorizontalDeviceMetricsTable();
+
+  int32_t Version();
+  int32_t NumRecords();
+  int32_t RecordSize();
+  int32_t PixelSize(int32_t record_index);
+  int32_t MaxWidth(int32_t record_index);
+  int32_t Width(int32_t record_index, int32_t glyph_num);
+
+ private:
+  struct Offset {
+    enum {
+      kVersion = 0,
+      kNumRecords = 2,
+      kSizeDeviceRecord = 4,
+      kRecords = 8,
+
+      // Offsets within a device record
+      kDeviceRecordPixelSize = 0,
+      kDeviceRecordMaxWidth = 1,
+      kDeviceRecordWidths = 2,
+    };
+  };
+  HorizontalDeviceMetricsTable(Header* header,
+                               ReadableFontData* data,
+                               int32_t num_glyphs);
+
+  int32_t num_glyphs_;
+};
+typedef Ptr<HorizontalDeviceMetricsTable> HorizontalDeviceMetricsTablePtr;
+typedef Ptr<HorizontalDeviceMetricsTable::Builder>
+            HorizontalDeviceMetricsTableBuilderPtr;
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_DEVICE_METRICS_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/horizontal_header_table.cc b/sfntly/cpp/src/sfntly/table/core/horizontal_header_table.cc
new file mode 100644
index 0000000..43c2058
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/horizontal_header_table.cc
@@ -0,0 +1,213 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/core/horizontal_header_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * HorizontalHeaderTable class
+ ******************************************************************************/
+HorizontalHeaderTable:: ~HorizontalHeaderTable() {}
+
+int32_t HorizontalHeaderTable::TableVersion() {
+  return data_->ReadFixed(Offset::kVersion);
+}
+
+int32_t HorizontalHeaderTable::Ascender() {
+  return data_->ReadShort(Offset::kAscender);
+}
+
+int32_t HorizontalHeaderTable::Descender() {
+  return data_->ReadShort(Offset::kDescender);
+}
+
+int32_t HorizontalHeaderTable::LineGap() {
+  return data_->ReadShort(Offset::kLineGap);
+}
+
+int32_t HorizontalHeaderTable::AdvanceWidthMax() {
+  return data_->ReadUShort(Offset::kAdvanceWidthMax);
+}
+
+int32_t HorizontalHeaderTable::MinLeftSideBearing() {
+  return data_->ReadShort(Offset::kMinLeftSideBearing);
+}
+
+int32_t HorizontalHeaderTable::MinRightSideBearing() {
+  return data_->ReadShort(Offset::kMinRightSideBearing);
+}
+
+int32_t HorizontalHeaderTable::XMaxExtent() {
+  return data_->ReadShort(Offset::kXMaxExtent);
+}
+
+int32_t HorizontalHeaderTable::CaretSlopeRise() {
+  return data_->ReadShort(Offset::kCaretSlopeRise);
+}
+
+int32_t HorizontalHeaderTable::CaretSlopeRun() {
+  return data_->ReadShort(Offset::kCaretSlopeRun);
+}
+
+int32_t HorizontalHeaderTable::CaretOffset() {
+  return data_->ReadShort(Offset::kCaretOffset);
+}
+
+int32_t HorizontalHeaderTable::MetricDataFormat() {
+  return data_->ReadShort(Offset::kMetricDataFormat);
+}
+
+int32_t HorizontalHeaderTable::NumberOfHMetrics() {
+  return data_->ReadUShort(Offset::kNumberOfHMetrics);
+}
+
+HorizontalHeaderTable:: HorizontalHeaderTable(Header* header,
+                                              ReadableFontData* data)
+    : Table(header, data) {
+}
+
+/******************************************************************************
+ * HorizontalHeaderTable::Builder class
+ ******************************************************************************/
+HorizontalHeaderTable::Builder::Builder(Header* header, WritableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+HorizontalHeaderTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+HorizontalHeaderTable::Builder::~Builder() {}
+
+CALLER_ATTACH FontDataTable*
+    HorizontalHeaderTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new HorizontalHeaderTable(header(), data);
+  return table.Detach();
+}
+
+CALLER_ATTACH HorizontalHeaderTable::Builder*
+    HorizontalHeaderTable::Builder::CreateBuilder(Header* header,
+                                                  WritableFontData* data) {
+  Ptr<HorizontalHeaderTable::Builder> builder;
+  builder = new HorizontalHeaderTable::Builder(header, data);
+  return builder.Detach();
+}
+
+int32_t HorizontalHeaderTable::Builder::TableVersion() {
+  return InternalReadData()->ReadFixed(Offset::kVersion);
+}
+
+void HorizontalHeaderTable::Builder::SetTableVersion(int32_t version) {
+  InternalWriteData()->WriteFixed(Offset::kVersion, version);
+}
+
+int32_t HorizontalHeaderTable::Builder::Ascender() {
+  return InternalReadData()->ReadShort(Offset::kAscender);
+}
+
+void HorizontalHeaderTable::Builder::SetAscender(int32_t ascender) {
+  InternalWriteData()->WriteShort(Offset::kVersion, ascender);
+}
+
+int32_t HorizontalHeaderTable::Builder::Descender() {
+  return InternalReadData()->ReadShort(Offset::kDescender);
+}
+
+void HorizontalHeaderTable::Builder::SetDescender(int32_t descender) {
+  InternalWriteData()->WriteShort(Offset::kDescender, descender);
+}
+
+int32_t HorizontalHeaderTable::Builder::LineGap() {
+  return InternalReadData()->ReadShort(Offset::kLineGap);
+}
+
+void HorizontalHeaderTable::Builder::SetLineGap(int32_t line_gap) {
+  InternalWriteData()->WriteShort(Offset::kLineGap, line_gap);
+}
+
+int32_t HorizontalHeaderTable::Builder::AdvanceWidthMax() {
+  return InternalReadData()->ReadUShort(Offset::kAdvanceWidthMax);
+}
+
+void HorizontalHeaderTable::Builder::SetAdvanceWidthMax(int32_t value) {
+  InternalWriteData()->WriteUShort(Offset::kAdvanceWidthMax, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::MinLeftSideBearing() {
+  return InternalReadData()->ReadShort(Offset::kMinLeftSideBearing);
+}
+
+void HorizontalHeaderTable::Builder::SetMinLeftSideBearing(int32_t value) {
+  InternalWriteData()->WriteShort(Offset::kMinLeftSideBearing, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::MinRightSideBearing() {
+  return InternalReadData()->ReadShort(Offset::kMinRightSideBearing);
+}
+
+void HorizontalHeaderTable::Builder::SetMinRightSideBearing(int32_t value) {
+  InternalWriteData()->WriteShort(Offset::kMinRightSideBearing, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::XMaxExtent() {
+  return InternalReadData()->ReadShort(Offset::kXMaxExtent);
+}
+
+void HorizontalHeaderTable::Builder::SetXMaxExtent(int32_t value) {
+  InternalWriteData()->WriteShort(Offset::kXMaxExtent, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::CaretSlopeRise() {
+  return InternalReadData()->ReadUShort(Offset::kCaretSlopeRise);
+}
+
+void HorizontalHeaderTable::Builder::SetCaretSlopeRise(int32_t value) {
+  InternalWriteData()->WriteUShort(Offset::kCaretSlopeRise, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::CaretSlopeRun() {
+  return InternalReadData()->ReadUShort(Offset::kCaretSlopeRun);
+}
+
+void HorizontalHeaderTable::Builder::SetCaretSlopeRun(int32_t value) {
+  InternalWriteData()->WriteUShort(Offset::kCaretSlopeRun, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::CaretOffset() {
+  return InternalReadData()->ReadUShort(Offset::kCaretOffset);
+}
+
+void HorizontalHeaderTable::Builder::SetCaretOffset(int32_t value) {
+  InternalWriteData()->WriteUShort(Offset::kCaretOffset, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::MetricDataFormat() {
+  return InternalReadData()->ReadUShort(Offset::kMetricDataFormat);
+}
+
+void HorizontalHeaderTable::Builder::SetMetricDataFormat(int32_t value) {
+  InternalWriteData()->WriteUShort(Offset::kMetricDataFormat, value);
+}
+
+int32_t HorizontalHeaderTable::Builder::NumberOfHMetrics() {
+  return InternalReadData()->ReadUShort(Offset::kNumberOfHMetrics);
+}
+
+void HorizontalHeaderTable::Builder::SetNumberOfHMetrics(int32_t value) {
+  InternalWriteData()->WriteUShort(Offset::kNumberOfHMetrics, value);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/horizontal_header_table.h b/sfntly/cpp/src/sfntly/table/core/horizontal_header_table.h
new file mode 100644
index 0000000..71f30b4
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/horizontal_header_table.h
@@ -0,0 +1,111 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_HEADER_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_HEADER_TABLE_H_
+
+#include "sfntly/table/table.h"
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+// A Horizontal Header table - 'hhea'.
+class HorizontalHeaderTable : public Table,
+                              public RefCounted<HorizontalHeaderTable> {
+ public:
+  // Builder for a Horizontal Header table - 'hhea'.
+  class Builder : public TableBasedTableBuilder, public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    int32_t TableVersion();
+    void SetTableVersion(int32_t version);
+    int32_t Ascender();
+    void SetAscender(int32_t ascender);
+    int32_t Descender();
+    void SetDescender(int32_t descender);
+    int32_t LineGap();
+    void SetLineGap(int32_t line_gap);
+    int32_t AdvanceWidthMax();
+    void SetAdvanceWidthMax(int32_t value);
+    int32_t MinLeftSideBearing();
+    void SetMinLeftSideBearing(int32_t value);
+    int32_t MinRightSideBearing();
+    void SetMinRightSideBearing(int32_t value);
+    int32_t XMaxExtent();
+    void SetXMaxExtent(int32_t value);
+    int32_t CaretSlopeRise();
+    void SetCaretSlopeRise(int32_t value);
+    int32_t CaretSlopeRun();
+    void SetCaretSlopeRun(int32_t value);
+    int32_t CaretOffset();
+    void SetCaretOffset(int32_t value);
+    int32_t MetricDataFormat();
+    void SetMetricDataFormat(int32_t value);
+    int32_t NumberOfHMetrics();
+    void SetNumberOfHMetrics(int32_t value);
+  };
+
+  virtual ~HorizontalHeaderTable();
+  int32_t TableVersion();
+  int32_t Ascender();
+  int32_t Descender();
+  int32_t LineGap();
+  int32_t AdvanceWidthMax();
+  int32_t MinLeftSideBearing();
+  int32_t MinRightSideBearing();
+  int32_t XMaxExtent();
+  int32_t CaretSlopeRise();
+  int32_t CaretSlopeRun();
+  int32_t CaretOffset();
+  int32_t MetricDataFormat();
+  int32_t NumberOfHMetrics();
+
+ private:
+  struct Offset {
+    enum {
+      kVersion = 0,
+      kAscender = 4,
+      kDescender = 6,
+      kLineGap = 8,
+      kAdvanceWidthMax = 10,
+      kMinLeftSideBearing = 12,
+      kMinRightSideBearing = 14,
+      kXMaxExtent = 16,
+      kCaretSlopeRise = 18,
+      kCaretSlopeRun = 20,
+      kCaretOffset = 22,
+      kMetricDataFormat = 32,
+      kNumberOfHMetrics = 34,
+    };
+  };
+
+  HorizontalHeaderTable(Header* header, ReadableFontData* data);
+};
+typedef Ptr<HorizontalHeaderTable> HorizontalHeaderTablePtr;
+typedef Ptr<HorizontalHeaderTable::Builder> HorizontalHeaderTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_HEADER_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/horizontal_metrics_table.cc b/sfntly/cpp/src/sfntly/table/core/horizontal_metrics_table.cc
new file mode 100644
index 0000000..156387d
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/horizontal_metrics_table.cc
@@ -0,0 +1,138 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/core/horizontal_metrics_table.h"
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+/******************************************************************************
+ * HorizontalMetricsTable class
+ ******************************************************************************/
+HorizontalMetricsTable::~HorizontalMetricsTable() {}
+
+int32_t HorizontalMetricsTable::NumberOfHMetrics() {
+  return num_hmetrics_;
+}
+
+int32_t HorizontalMetricsTable::NumberOfLSBs() {
+  return num_glyphs_ - num_hmetrics_;
+}
+
+int32_t HorizontalMetricsTable::HMetricAdvanceWidth(int32_t entry) {
+  if (entry > num_hmetrics_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#endif
+    return 0;
+  }
+  int32_t offset = Offset::kHMetricsStart + (entry * Offset::kHMetricsSize) +
+                   Offset::kHMetricsAdvanceWidth;
+  return data_->ReadUShort(offset);
+}
+
+int32_t HorizontalMetricsTable::HMetricLSB(int32_t entry) {
+  if (entry > num_hmetrics_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#endif
+    return 0;
+  }
+  int32_t offset = Offset::kHMetricsStart + (entry * Offset::kHMetricsSize) +
+                   Offset::kHMetricsLeftSideBearing;
+  return data_->ReadShort(offset);
+}
+
+int32_t HorizontalMetricsTable::LsbTableEntry(int32_t entry) {
+  if (entry > num_hmetrics_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#endif
+    return 0;
+  }
+  int32_t offset = Offset::kHMetricsStart + (entry * Offset::kHMetricsSize) +
+                   Offset::kLeftSideBearingSize;
+  return data_->ReadShort(offset);
+}
+
+int32_t HorizontalMetricsTable::AdvanceWidth(int32_t glyph_id) {
+  if (glyph_id < num_hmetrics_) {
+    return HMetricAdvanceWidth(glyph_id);
+  }
+  return HMetricAdvanceWidth(glyph_id - num_hmetrics_);
+}
+
+int32_t HorizontalMetricsTable::LeftSideBearing(int32_t glyph_id) {
+  if (glyph_id < num_hmetrics_) {
+    return HMetricLSB(glyph_id);
+  }
+  return LsbTableEntry(glyph_id - num_hmetrics_);
+}
+
+HorizontalMetricsTable::HorizontalMetricsTable(Header* header,
+                                               ReadableFontData* data,
+                                               int32_t num_hmetrics,
+                                               int32_t num_glyphs)
+    : Table(header, data),
+      num_hmetrics_(num_hmetrics),
+      num_glyphs_(num_glyphs) {
+}
+
+/******************************************************************************
+ * HorizontalMetricsTable::Builder class
+ ******************************************************************************/
+HorizontalMetricsTable::Builder::Builder(Header* header, WritableFontData* data)
+    : TableBasedTableBuilder(header, data), num_hmetrics_(-1), num_glyphs_(-1) {
+}
+
+HorizontalMetricsTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : TableBasedTableBuilder(header, data), num_hmetrics_(-1), num_glyphs_(-1) {
+}
+
+HorizontalMetricsTable::Builder::~Builder() {}
+
+CALLER_ATTACH FontDataTable*
+    HorizontalMetricsTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table =
+      new HorizontalMetricsTable(header(), data, num_hmetrics_, num_glyphs_);
+  return table.Detach();
+}
+
+CALLER_ATTACH HorizontalMetricsTable::Builder*
+    HorizontalMetricsTable::Builder::CreateBuilder(Header* header,
+                                                   WritableFontData* data) {
+  Ptr<HorizontalMetricsTable::Builder> builder;
+  builder = new HorizontalMetricsTable::Builder(header, data);
+  return builder.Detach();
+}
+
+void HorizontalMetricsTable::Builder::SetNumberOfHMetrics(
+    int32_t num_hmetrics) {
+  assert(num_hmetrics >= 0);
+  num_hmetrics_ = num_hmetrics;
+  HorizontalMetricsTable* table =
+      down_cast<HorizontalMetricsTable*>(this->GetTable());
+  table->num_hmetrics_ = num_hmetrics;
+}
+
+void HorizontalMetricsTable::Builder::SetNumGlyphs(int32_t num_glyphs) {
+  assert(num_glyphs >= 0);
+  num_glyphs_ = num_glyphs;
+  HorizontalMetricsTable* table =
+      down_cast<HorizontalMetricsTable*>(this->GetTable());
+  table->num_glyphs_ = num_glyphs;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/horizontal_metrics_table.h b/sfntly/cpp/src/sfntly/table/core/horizontal_metrics_table.h
new file mode 100644
index 0000000..44b51f2
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/horizontal_metrics_table.h
@@ -0,0 +1,87 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_METRICS_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_METRICS_TABLE_H_
+
+#include "sfntly/table/table.h"
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+// A Horizontal Metrics table - 'hmtx'.
+class HorizontalMetricsTable : public Table,
+                               public RefCounted<HorizontalMetricsTable> {
+ public:
+  // Builder for a Horizontal Metrics Table - 'hmtx'.
+  class Builder : public TableBasedTableBuilder, public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    void SetNumberOfHMetrics(int32_t num_hmetrics);
+    void SetNumGlyphs(int32_t num_glyphs);
+
+   private:
+    int32_t num_hmetrics_;
+    int32_t num_glyphs_;
+  };
+
+  virtual ~HorizontalMetricsTable();
+  int32_t NumberOfHMetrics();
+  int32_t NumberOfLSBs();
+  int32_t HMetricAdvanceWidth(int32_t entry);
+  int32_t HMetricLSB(int32_t entry);
+  int32_t LsbTableEntry(int32_t entry);
+  int32_t AdvanceWidth(int32_t glyph_id);
+  int32_t LeftSideBearing(int32_t glyph_id);
+
+ private:
+  struct Offset {
+    enum {
+      // hMetrics
+      kHMetricsStart = 0,
+      kHMetricsSize = 4,
+
+      // Offset within an hMetric
+      kHMetricsAdvanceWidth = 0,
+      kHMetricsLeftSideBearing = 2,
+
+      kLeftSideBearingSize = 2
+    };
+  };
+
+  HorizontalMetricsTable(Header* header,
+                         ReadableFontData* data,
+                         int32_t num_hmetrics,
+                         int32_t num_glyphs);
+
+  int32_t num_hmetrics_;
+  int32_t num_glyphs_;
+};
+typedef Ptr<HorizontalMetricsTable> HorizontalMetricsTablePtr;
+typedef Ptr<HorizontalMetricsTable::Builder> HorizontalMetricsTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_HORIZONTAL_METRICS_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/maximum_profile_table.cc b/sfntly/cpp/src/sfntly/table/core/maximum_profile_table.cc
new file mode 100644
index 0000000..a8ac3bc
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/maximum_profile_table.cc
@@ -0,0 +1,240 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/core/maximum_profile_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * MaximumProfileTable class
+ ******************************************************************************/
+MaximumProfileTable::~MaximumProfileTable() {}
+
+int32_t MaximumProfileTable::TableVersion() {
+  return data_->ReadFixed(Offset::kVersion);
+}
+
+int32_t MaximumProfileTable::NumGlyphs() {
+  return data_->ReadUShort(Offset::kNumGlyphs);
+}
+
+int32_t MaximumProfileTable::MaxPoints() {
+  return data_->ReadUShort(Offset::kMaxPoints);
+}
+
+int32_t MaximumProfileTable::MaxContours() {
+  return data_->ReadUShort(Offset::kMaxContours);
+}
+
+int32_t MaximumProfileTable::MaxCompositePoints() {
+  return data_->ReadUShort(Offset::kMaxCompositePoints);
+}
+
+int32_t MaximumProfileTable::MaxCompositeContours() {
+  return data_->ReadUShort(Offset::kMaxCompositeContours);
+}
+
+int32_t MaximumProfileTable::MaxZones() {
+  return data_->ReadUShort(Offset::kMaxZones);
+}
+
+int32_t MaximumProfileTable::MaxTwilightPoints() {
+  return data_->ReadUShort(Offset::kMaxTwilightPoints);
+}
+
+int32_t MaximumProfileTable::MaxStorage() {
+  return data_->ReadUShort(Offset::kMaxStorage);
+}
+
+int32_t MaximumProfileTable::MaxFunctionDefs() {
+  return data_->ReadUShort(Offset::kMaxFunctionDefs);
+}
+
+int32_t MaximumProfileTable::MaxStackElements() {
+  return data_->ReadUShort(Offset::kMaxStackElements);
+}
+
+int32_t MaximumProfileTable::MaxSizeOfInstructions() {
+  return data_->ReadUShort(Offset::kMaxSizeOfInstructions);
+}
+
+int32_t MaximumProfileTable::MaxComponentElements() {
+  return data_->ReadUShort(Offset::kMaxComponentElements);
+}
+
+int32_t MaximumProfileTable::MaxComponentDepth() {
+  return data_->ReadUShort(Offset::kMaxComponentDepth);
+}
+
+MaximumProfileTable::MaximumProfileTable(Header* header,
+                                         ReadableFontData* data)
+    : Table(header, data) {
+}
+
+/******************************************************************************
+ * MaximumProfileTable::Builder class
+ ******************************************************************************/
+MaximumProfileTable::Builder::Builder(Header* header, WritableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+MaximumProfileTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+MaximumProfileTable::Builder::~Builder() {}
+
+CALLER_ATTACH FontDataTable*
+    MaximumProfileTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new MaximumProfileTable(header(), data);
+  return table.Detach();
+}
+
+CALLER_ATTACH MaximumProfileTable::Builder*
+    MaximumProfileTable::Builder::CreateBuilder(Header* header,
+                                                WritableFontData* data) {
+  Ptr<MaximumProfileTable::Builder> builder;
+  builder = new MaximumProfileTable::Builder(header, data);
+  return builder.Detach();
+}
+
+int32_t MaximumProfileTable::Builder::TableVersion() {
+  return InternalReadData()->ReadUShort(Offset::kVersion);
+}
+
+void MaximumProfileTable::Builder::SetTableVersion(int32_t version) {
+  InternalWriteData()->WriteUShort(Offset::kVersion, version);
+}
+
+int32_t MaximumProfileTable::Builder::NumGlyphs() {
+  return InternalReadData()->ReadUShort(Offset::kNumGlyphs);
+}
+
+void MaximumProfileTable::Builder::SetNumGlyphs(int32_t num_glyphs) {
+  InternalWriteData()->WriteUShort(Offset::kNumGlyphs, num_glyphs);
+}
+
+int32_t MaximumProfileTable::Builder::MaxPoints() {
+  return InternalReadData()->ReadUShort(Offset::kMaxPoints);
+}
+
+void MaximumProfileTable::Builder::SetMaxPoints(int32_t max_points) {
+  InternalWriteData()->WriteUShort(Offset::kMaxPoints, max_points);
+}
+
+int32_t MaximumProfileTable::Builder::MaxContours() {
+  return InternalReadData()->ReadUShort(Offset::kMaxContours);
+}
+
+void MaximumProfileTable::Builder::SetMaxContours(int32_t max_contours) {
+  InternalWriteData()->WriteUShort(Offset::kMaxContours, max_contours);
+}
+
+int32_t MaximumProfileTable::Builder::MaxCompositePoints() {
+  return InternalReadData()->ReadUShort(Offset::kMaxCompositePoints);
+}
+
+void MaximumProfileTable::Builder::SetMaxCompositePoints(
+    int32_t max_composite_points) {
+  InternalWriteData()->WriteUShort(Offset::kMaxCompositePoints,
+                                   max_composite_points);
+}
+
+int32_t MaximumProfileTable::Builder::MaxCompositeContours() {
+  return InternalReadData()->ReadUShort(Offset::kMaxCompositeContours);
+}
+
+void MaximumProfileTable::Builder::SetMaxCompositeContours(
+    int32_t max_composite_contours) {
+  InternalWriteData()->WriteUShort(Offset::kMaxCompositeContours,
+      max_composite_contours);
+}
+
+int32_t MaximumProfileTable::Builder::MaxZones() {
+  return InternalReadData()->ReadUShort(Offset::kMaxZones);
+}
+
+void MaximumProfileTable::Builder::SetMaxZones(int32_t max_zones) {
+  InternalWriteData()->WriteUShort(Offset::kMaxZones, max_zones);
+}
+
+int32_t MaximumProfileTable::Builder::MaxTwilightPoints() {
+  return InternalReadData()->ReadUShort(Offset::kMaxTwilightPoints);
+}
+
+void MaximumProfileTable::Builder::SetMaxTwilightPoints(
+    int32_t max_twilight_points) {
+  InternalWriteData()->WriteUShort(Offset::kMaxTwilightPoints,
+                                   max_twilight_points);
+}
+
+int32_t MaximumProfileTable::Builder::MaxStorage() {
+  return InternalReadData()->ReadUShort(Offset::kMaxStorage);
+}
+
+void MaximumProfileTable::Builder::SetMaxStorage(int32_t max_storage) {
+  InternalWriteData()->WriteUShort(Offset::kMaxStorage, max_storage);
+}
+
+int32_t MaximumProfileTable::Builder::MaxFunctionDefs() {
+  return InternalReadData()->ReadUShort(Offset::kMaxFunctionDefs);
+}
+
+void MaximumProfileTable::Builder::SetMaxFunctionDefs(
+    int32_t max_function_defs) {
+  InternalWriteData()->WriteUShort(Offset::kMaxFunctionDefs, max_function_defs);
+}
+
+int32_t MaximumProfileTable::Builder::MaxStackElements() {
+  return InternalReadData()->ReadUShort(Offset::kMaxStackElements);
+}
+
+void MaximumProfileTable::Builder::SetMaxStackElements(
+    int32_t max_stack_elements) {
+  InternalWriteData()->WriteUShort(Offset::kMaxStackElements,
+                                   max_stack_elements);
+}
+
+int32_t MaximumProfileTable::Builder::MaxSizeOfInstructions() {
+  return InternalReadData()->ReadUShort(Offset::kMaxSizeOfInstructions);
+}
+
+void MaximumProfileTable::Builder::SetMaxSizeOfInstructions(
+    int32_t max_size_of_instructions) {
+  InternalWriteData()->WriteUShort(Offset::kMaxSizeOfInstructions,
+                                   max_size_of_instructions);
+}
+
+int32_t MaximumProfileTable::Builder::MaxComponentElements() {
+  return InternalReadData()->ReadUShort(Offset::kMaxComponentElements);
+}
+
+void MaximumProfileTable::Builder::SetMaxComponentElements(
+    int32_t max_component_elements) {
+  InternalWriteData()->WriteUShort(Offset::kMaxComponentElements,
+                                   max_component_elements);
+}
+
+int32_t MaximumProfileTable::Builder::MaxComponentDepth() {
+  return InternalReadData()->ReadUShort(Offset::kMaxComponentDepth);
+}
+
+void MaximumProfileTable::Builder::SetMaxComponentDepth(
+    int32_t max_component_depth) {
+  InternalWriteData()->WriteUShort(Offset::kMaxComponentDepth,
+                                   max_component_depth);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/maximum_profile_table.h b/sfntly/cpp/src/sfntly/table/core/maximum_profile_table.h
new file mode 100644
index 0000000..e7c5abb
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/maximum_profile_table.h
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_MAXIMUM_PROFILE_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_MAXIMUM_PROFILE_TABLE_H_
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/table/table.h"
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+// A Maximum Profile table - 'maxp'.
+class MaximumProfileTable : public Table,
+                            public RefCounted<MaximumProfileTable> {
+ public:
+  // Builder for a Maximum Profile table - 'maxp'.
+  class Builder : public TableBasedTableBuilder, public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    int32_t TableVersion();
+    void SetTableVersion(int32_t version);
+    int32_t NumGlyphs();
+    void SetNumGlyphs(int32_t num_glyphs);
+    int32_t MaxPoints();
+    void SetMaxPoints(int32_t max_points);
+    int32_t MaxContours();
+    void SetMaxContours(int32_t max_contours);
+    int32_t MaxCompositePoints();
+    void SetMaxCompositePoints(int32_t max_composite_points);
+    int32_t MaxCompositeContours();
+    void SetMaxCompositeContours(int32_t max_composite_contours);
+    int32_t MaxZones();
+    void SetMaxZones(int32_t max_zones);
+    int32_t MaxTwilightPoints();
+    void SetMaxTwilightPoints(int32_t max_twilight_points);
+    int32_t MaxStorage();
+    void SetMaxStorage(int32_t max_storage);
+    int32_t MaxFunctionDefs();
+    void SetMaxFunctionDefs(int32_t max_function_defs);
+    int32_t MaxStackElements();
+    void SetMaxStackElements(int32_t max_stack_elements);
+    int32_t MaxSizeOfInstructions();
+    void SetMaxSizeOfInstructions(int32_t max_size_of_instructions);
+    int32_t MaxComponentElements();
+    void SetMaxComponentElements(int32_t max_component_elements);
+    int32_t MaxComponentDepth();
+    void SetMaxComponentDepth(int32_t max_component_depth);
+  };
+
+  virtual ~MaximumProfileTable();
+  int32_t TableVersion();
+  int32_t NumGlyphs();
+  int32_t MaxPoints();
+  int32_t MaxContours();
+  int32_t MaxCompositePoints();
+  int32_t MaxCompositeContours();
+  int32_t MaxZones();
+  int32_t MaxTwilightPoints();
+  int32_t MaxStorage();
+  int32_t MaxFunctionDefs();
+  int32_t MaxStackElements();
+  int32_t MaxSizeOfInstructions();
+  int32_t MaxComponentElements();
+  int32_t MaxComponentDepth();
+
+ private:
+  struct Offset {
+    enum {
+      // version 0.5 and 1.0
+      kVersion = 0,
+      kNumGlyphs = 4,
+
+      // version 1.0
+      kMaxPoints = 6,
+      kMaxContours = 8,
+      kMaxCompositePoints = 10,
+      kMaxCompositeContours = 12,
+      kMaxZones = 14,
+      kMaxTwilightPoints = 16,
+      kMaxStorage = 18,
+      kMaxFunctionDefs = 20,
+      kMaxInstructionDefs = 22,
+      kMaxStackElements = 24,
+      kMaxSizeOfInstructions = 26,
+      kMaxComponentElements = 28,
+      kMaxComponentDepth = 30,
+    };
+  };
+
+  MaximumProfileTable(Header* header, ReadableFontData* data);
+};
+typedef Ptr<MaximumProfileTable> MaximumProfileTablePtr;
+typedef Ptr<MaximumProfileTable::Builder> MaximumProfileTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_MAXIMUM_PROFILE_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/name_table.cc b/sfntly/cpp/src/sfntly/table/core/name_table.cc
new file mode 100644
index 0000000..8d2f64f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/name_table.cc
@@ -0,0 +1,723 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/core/name_table.h"
+
+#include <stdio.h>
+#include <string.h>
+
+#include <unicode/unistr.h>
+
+#include "sfntly/font.h"
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+/******************************************************************************
+ * NameTable::NameEntryId class
+ ******************************************************************************/
+NameTable::NameEntryId::NameEntryId()
+    : platform_id_(0),
+      encoding_id_(0),
+      language_id_(0),
+      name_id_(0) {
+}
+
+NameTable::NameEntryId::NameEntryId(int32_t platform_id,
+                                    int32_t encoding_id,
+                                    int32_t language_id,
+                                    int32_t name_id)
+    : platform_id_(platform_id),
+      encoding_id_(encoding_id),
+      language_id_(language_id),
+      name_id_(name_id) {
+}
+
+NameTable::NameEntryId::NameEntryId(const NameTable::NameEntryId& rhs) {
+  *this = rhs;
+}
+
+const NameTable::NameEntryId&
+    NameTable::NameEntryId::operator=(const NameTable::NameEntryId& rhs) const {
+  platform_id_ = rhs.platform_id_;
+  encoding_id_ = rhs.encoding_id_;
+  language_id_ = rhs.language_id_;
+  name_id_ = rhs.name_id_;
+  return *this;
+}
+
+bool NameTable::NameEntryId::operator==(const NameEntryId& rhs) const {
+  return platform_id_ == rhs.platform_id_ &&
+         encoding_id_ == rhs.encoding_id_ &&
+         language_id_ == rhs.language_id_ &&
+         name_id_ == rhs.name_id_;
+}
+
+bool NameTable::NameEntryId::operator<(const NameEntryId& rhs) const {
+  if (platform_id_ != rhs.platform_id_) return platform_id_ < rhs.platform_id_;
+  if (encoding_id_ != rhs.encoding_id_) return encoding_id_ < rhs.encoding_id_;
+  if (language_id_ != rhs.language_id_) return language_id_ < rhs.language_id_;
+  return name_id_ < rhs.name_id_;
+}
+
+/******************************************************************************
+ * NameTable::NameEntry class
+ ******************************************************************************/
+NameTable::NameEntry::NameEntry() {
+  Init(0, 0, 0, 0, NULL);
+}
+
+NameTable::NameEntry::NameEntry(const NameEntryId& name_entry_id,
+                                const ByteVector& name_bytes) {
+  Init(name_entry_id.platform_id(),
+       name_entry_id.encoding_id(),
+       name_entry_id.language_id(),
+       name_entry_id.name_id(),
+       &name_bytes);
+}
+
+NameTable::NameEntry::NameEntry(int32_t platform_id,
+                                int32_t encoding_id,
+                                int32_t language_id,
+                                int32_t name_id,
+                                const ByteVector& name_bytes) {
+  Init(platform_id, encoding_id, language_id, name_id, &name_bytes);
+}
+
+NameTable::NameEntry::~NameEntry() {}
+
+ByteVector* NameTable::NameEntry::NameAsBytes() {
+  return &name_bytes_;
+}
+
+int32_t NameTable::NameEntry::NameBytesLength() {
+  return name_bytes_.size();
+}
+
+UChar* NameTable::NameEntry::Name() {
+  return NameTable::ConvertFromNameBytes(&name_bytes_,
+                                         platform_id(),
+                                         encoding_id());
+}
+
+bool NameTable::NameEntry::operator==(const NameEntry& rhs) const {
+  return (name_entry_id_ == rhs.name_entry_id_ &&
+          name_bytes_ == rhs.name_bytes_);
+}
+
+void NameTable::NameEntry::Init(int32_t platform_id,
+                                int32_t encoding_id,
+                                int32_t language_id,
+                                int32_t name_id,
+                                const ByteVector* name_bytes) {
+  name_entry_id_ = NameEntryId(platform_id, encoding_id, language_id, name_id);
+  if (name_bytes) {
+    name_bytes_ = *name_bytes;
+  } else {
+    name_bytes_.clear();
+  }
+}
+
+/******************************************************************************
+ * NameTable::NameEntryBuilder class
+ ******************************************************************************/
+NameTable::NameEntryBuilder::NameEntryBuilder() {
+  Init(0, 0, 0, 0, NULL);
+}
+
+NameTable::NameEntryBuilder::NameEntryBuilder(const NameEntryId& name_entry_id,
+                                              const ByteVector& name_bytes) {
+  Init(name_entry_id.platform_id(),
+       name_entry_id.encoding_id(),
+       name_entry_id.language_id(),
+       name_entry_id.name_id(),
+       &name_bytes);
+}
+
+NameTable::NameEntryBuilder::NameEntryBuilder(
+    const NameEntryId& name_entry_id) {
+  Init(name_entry_id.platform_id(),
+       name_entry_id.encoding_id(),
+       name_entry_id.language_id(),
+       name_entry_id.name_id(),
+       NULL);
+}
+
+NameTable::NameEntryBuilder::NameEntryBuilder(NameEntry* b) {
+  Init(b->platform_id(),
+       b->encoding_id(),
+       b->language_id(),
+       b->name_id(),
+       b->NameAsBytes());
+}
+
+NameTable::NameEntryBuilder::~NameEntryBuilder() {}
+
+void NameTable::NameEntryBuilder::SetName(const UChar* name) {
+  if (name == NULL) {
+    name_entry_->name_bytes_.clear();
+    return;
+  }
+  NameTable::ConvertToNameBytes(name,
+                                name_entry_->platform_id(),
+                                name_entry_->encoding_id(),
+                                &name_entry_->name_bytes_);
+}
+
+void NameTable::NameEntryBuilder::SetName(const ByteVector& name_bytes) {
+  name_entry_->name_bytes_.clear();
+  std::copy(name_bytes.begin(),
+            name_bytes.end(),
+            name_entry_->name_bytes_.begin());
+}
+
+void NameTable::NameEntryBuilder::SetName(const ByteVector& name_bytes,
+                                          int32_t offset,
+                                          int32_t length) {
+  name_entry_->name_bytes_.clear();
+  std::copy(name_bytes.begin() + offset,
+            name_bytes.begin() + offset + length,
+            name_entry_->name_bytes_.begin());
+}
+
+void NameTable::NameEntryBuilder::Init(int32_t platform_id,
+                                       int32_t encoding_id,
+                                       int32_t language_id,
+                                       int32_t name_id,
+                                       const ByteVector* name_bytes) {
+  name_entry_ = new NameEntry();
+  name_entry_->Init(platform_id, encoding_id, language_id, name_id, name_bytes);
+}
+
+/******************************************************************************
+ * NameTable::NameEntryFilterInPlace class (C++ port only)
+ ******************************************************************************/
+NameTable::NameEntryFilterInPlace::NameEntryFilterInPlace(int32_t platform_id,
+                                                          int32_t encoding_id,
+                                                          int32_t language_id,
+                                                          int32_t name_id)
+    : platform_id_(platform_id),
+      encoding_id_(encoding_id),
+      language_id_(language_id),
+      name_id_(name_id) {
+}
+
+bool NameTable::NameEntryFilterInPlace::Accept(int32_t platform_id,
+                                               int32_t encoding_id,
+                                               int32_t language_id,
+                                               int32_t name_id) {
+  return (platform_id_ == platform_id &&
+          encoding_id_ == encoding_id &&
+          language_id_ == language_id &&
+          name_id_ == name_id);
+}
+
+/******************************************************************************
+ * NameTable::NameEntryIterator class
+ ******************************************************************************/
+NameTable::NameEntryIterator::NameEntryIterator(NameTable* table)
+    : RefIterator<NameEntry, NameTable>(table),
+      name_index_(0),
+      filter_(NULL) {
+}
+
+NameTable::NameEntryIterator::NameEntryIterator(NameTable* table,
+                                                NameEntryFilter* filter)
+    : RefIterator<NameEntry, NameTable>(table),
+      name_index_(0),
+      filter_(filter) {
+}
+
+bool NameTable::NameEntryIterator::HasNext() {
+  if (!filter_) {
+    if (name_index_ < container()->NameCount()) {
+      return true;
+    }
+    return false;
+  }
+  for (; name_index_ < container()->NameCount(); ++name_index_) {
+    if (filter_->Accept(container()->PlatformId(name_index_),
+                        container()->EncodingId(name_index_),
+                        container()->LanguageId(name_index_),
+                        container()->NameId(name_index_))) {
+      return true;
+    }
+  }
+  return false;
+}
+
+CALLER_ATTACH NameTable::NameEntry* NameTable::NameEntryIterator::Next() {
+  if (!HasNext())
+    return NULL;
+  return container()->GetNameEntry(name_index_++);
+}
+
+/******************************************************************************
+ * NameTable::Builder class
+ ******************************************************************************/
+NameTable::Builder::Builder(Header* header, WritableFontData* data)
+    : SubTableContainerTable::Builder(header, data) {
+}
+
+NameTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : SubTableContainerTable::Builder(header, data) {
+}
+
+CALLER_ATTACH NameTable::Builder*
+    NameTable::Builder::CreateBuilder(Header* header,
+                                      WritableFontData* data) {
+  Ptr<NameTable::Builder> builder;
+  builder = new NameTable::Builder(header, data);
+  return builder.Detach();
+}
+
+void NameTable::Builder::RevertNames() {
+  name_entry_map_.clear();
+  set_model_changed(false);
+}
+
+int32_t NameTable::Builder::BuilderCount() {
+  GetNameBuilders();  // Ensure name_entry_map_ is built.
+  return (int32_t)name_entry_map_.size();
+}
+
+bool NameTable::Builder::Has(int32_t platform_id,
+                             int32_t encoding_id,
+                             int32_t language_id,
+                             int32_t name_id) {
+  NameEntryId probe(platform_id, encoding_id, language_id, name_id);
+  GetNameBuilders();  // Ensure name_entry_map_ is built.
+  return (name_entry_map_.find(probe) != name_entry_map_.end());
+}
+
+CALLER_ATTACH NameTable::NameEntryBuilder*
+    NameTable::Builder::NameBuilder(int32_t platform_id,
+                                    int32_t encoding_id,
+                                    int32_t language_id,
+                                    int32_t name_id) {
+  NameEntryId probe(platform_id, encoding_id, language_id, name_id);
+  NameEntryBuilderMap builders;
+  GetNameBuilders();  // Ensure name_entry_map_ is built.
+  if (name_entry_map_.find(probe) != name_entry_map_.end()) {
+    return name_entry_map_[probe];
+  }
+  NameEntryBuilderPtr builder = new NameEntryBuilder(probe);
+  name_entry_map_[probe] = builder;
+  return builder.Detach();
+}
+
+bool NameTable::Builder::Remove(int32_t platform_id,
+                                int32_t encoding_id,
+                                int32_t language_id,
+                                int32_t name_id) {
+  NameEntryId probe(platform_id, encoding_id, language_id, name_id);
+  GetNameBuilders();  // Ensure name_entry_map_ is built.
+  NameEntryBuilderMap::iterator position = name_entry_map_.find(probe);
+  if (position != name_entry_map_.end()) {
+    name_entry_map_.erase(position);
+    return true;
+  }
+  return false;
+}
+
+CALLER_ATTACH FontDataTable*
+    NameTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new NameTable(header(), data);
+  return table.Detach();
+}
+
+void NameTable::Builder::SubDataSet() {
+  name_entry_map_.clear();
+  set_model_changed(false);
+}
+
+int32_t NameTable::Builder::SubDataSizeToSerialize() {
+  if (name_entry_map_.empty()) {
+    return 0;
+  }
+
+  int32_t size = NameTable::Offset::kNameRecordStart +
+                 name_entry_map_.size() * NameTable::Offset::kNameRecordSize;
+  for (NameEntryBuilderMap::iterator b = name_entry_map_.begin(),
+                                     end = name_entry_map_.end();
+                                     b != end; ++b) {
+    NameEntryBuilderPtr p = b->second;
+    NameEntry* entry = p->name_entry();
+    size += entry->NameBytesLength();
+  }
+  return size;
+}
+
+bool NameTable::Builder::SubReadyToSerialize() {
+  return !name_entry_map_.empty();
+}
+
+int32_t NameTable::Builder::SubSerialize(WritableFontData* new_data) {
+  int32_t string_table_start_offset =
+      NameTable::Offset::kNameRecordStart +
+      name_entry_map_.size() * NameTable::Offset::kNameRecordSize;
+
+  // Header
+  new_data->WriteUShort(NameTable::Offset::kFormat, 0);
+  new_data->WriteUShort(NameTable::Offset::kCount, name_entry_map_.size());
+  new_data->WriteUShort(NameTable::Offset::kStringOffset,
+                        string_table_start_offset);
+  int32_t name_record_offset = NameTable::Offset::kNameRecordStart;
+  int32_t string_offset = 0;
+  // Note: we offered operator< in NameEntryId, which will be used by std::less,
+  //       and therefore our map will act like TreeMap in Java to provide
+  //       sorted key set.
+  for (NameEntryBuilderMap::iterator b = name_entry_map_.begin(),
+                                     end = name_entry_map_.end();
+                                     b != end; ++b) {
+    new_data->WriteUShort(
+        name_record_offset + NameTable::Offset::kNameRecordPlatformId,
+        b->first.platform_id());
+    new_data->WriteUShort(
+        name_record_offset + NameTable::Offset::kNameRecordEncodingId,
+        b->first.encoding_id());
+    new_data->WriteUShort(
+        name_record_offset + NameTable::Offset::kNameRecordLanguageId,
+        b->first.language_id());
+    new_data->WriteUShort(
+        name_record_offset + NameTable::Offset::kNameRecordNameId,
+        b->first.name_id());
+    NameEntry* builder_entry = b->second->name_entry();
+    new_data->WriteUShort(
+        name_record_offset + NameTable::Offset::kNameRecordStringLength,
+        builder_entry->NameBytesLength());
+    new_data->WriteUShort(
+        name_record_offset + NameTable::Offset::kNameRecordStringOffset,
+        string_offset);
+    name_record_offset += NameTable::Offset::kNameRecordSize;
+    string_offset += new_data->WriteBytes(
+        string_offset + string_table_start_offset,
+        builder_entry->NameAsBytes());
+  }
+
+  return string_offset + string_table_start_offset;
+}
+
+void NameTable::Builder::Initialize(ReadableFontData* data) {
+  if (data) {
+    NameTablePtr table = new NameTable(header(), data);
+    Ptr<NameEntryIterator> name_iter;
+    name_iter.Attach(table->Iterator());
+    while (name_iter->HasNext()) {
+      NameEntryPtr name_entry;
+      name_entry.Attach(name_iter->Next());
+      NameEntryBuilderPtr name_entry_builder = new NameEntryBuilder(name_entry);
+      NameEntry* builder_entry = name_entry_builder->name_entry();
+      NameEntryId probe = builder_entry->name_entry_id();
+      name_entry_map_[probe] = name_entry_builder;
+    }
+  }
+}
+
+NameTable::NameEntryBuilderMap* NameTable::Builder::GetNameBuilders() {
+  if (name_entry_map_.empty()) {
+    Initialize(InternalReadData());
+  }
+  set_model_changed();
+  return &name_entry_map_;
+}
+
+/******************************************************************************
+ * NameTable class
+ ******************************************************************************/
+NameTable::~NameTable() {}
+
+int32_t NameTable::Format() {
+  return data_->ReadUShort(Offset::kFormat);
+}
+
+int32_t NameTable::NameCount() {
+  return data_->ReadUShort(Offset::kCount);
+}
+
+int32_t NameTable::PlatformId(int32_t index) {
+  return data_->ReadUShort(Offset::kNameRecordPlatformId +
+                           OffsetForNameRecord(index));
+}
+
+int32_t NameTable::EncodingId(int32_t index) {
+  return data_->ReadUShort(Offset::kNameRecordEncodingId +
+                           OffsetForNameRecord(index));
+}
+
+int32_t NameTable::LanguageId(int32_t index) {
+  return data_->ReadUShort(Offset::kNameRecordLanguageId +
+                           OffsetForNameRecord(index));
+}
+
+int32_t NameTable::NameId(int32_t index) {
+  return data_->ReadUShort(Offset::kNameRecordNameId +
+                           OffsetForNameRecord(index));
+}
+
+void NameTable::NameAsBytes(int32_t index, ByteVector* b) {
+  assert(b);
+  int32_t length = NameLength(index);
+  b->clear();
+  b->resize(length);
+  if (length > 0) {
+    data_->ReadBytes(NameOffset(index), &((*b)[0]), 0, length);
+  }
+}
+
+void NameTable::NameAsBytes(int32_t platform_id,
+                            int32_t encoding_id,
+                            int32_t language_id,
+                            int32_t name_id,
+                            ByteVector* b) {
+  assert(b);
+  NameEntryPtr entry;
+  entry.Attach(GetNameEntry(platform_id, encoding_id, language_id, name_id));
+  if (entry) {
+    ByteVector* name = entry->NameAsBytes();
+    std::copy(name->begin(), name->end(), b->begin());
+  }
+}
+
+UChar* NameTable::Name(int32_t index) {
+  ByteVector b;
+  NameAsBytes(index, &b);
+  return ConvertFromNameBytes(&b, PlatformId(index), EncodingId(index));
+}
+
+UChar* NameTable::Name(int32_t platform_id,
+                       int32_t encoding_id,
+                       int32_t language_id,
+                       int32_t name_id) {
+  NameEntryPtr entry;
+  entry.Attach(GetNameEntry(platform_id, encoding_id, language_id, name_id));
+  if (entry) {
+    return entry->Name();
+  }
+  return NULL;
+}
+
+CALLER_ATTACH NameTable::NameEntry* NameTable::GetNameEntry(int32_t index) {
+  ByteVector b;
+  NameAsBytes(index, &b);
+  NameEntryPtr instance = new NameEntry(PlatformId(index),
+                                        EncodingId(index),
+                                        LanguageId(index),
+                                        NameId(index), b);
+  return instance.Detach();
+}
+
+CALLER_ATTACH NameTable::NameEntry* NameTable::GetNameEntry(int32_t platform_id,
+                                                            int32_t encoding_id,
+                                                            int32_t language_id,
+                                                            int32_t name_id) {
+  NameTable::NameEntryFilterInPlace
+      filter(platform_id, encoding_id, language_id, name_id);
+  Ptr<NameTable::NameEntryIterator> name_entry_iter;
+  name_entry_iter.Attach(Iterator(&filter));
+  NameEntryPtr result;
+  if (name_entry_iter->HasNext()) {
+    result = name_entry_iter->Next();
+  }
+  return result;
+}
+
+CALLER_ATTACH NameTable::NameEntryIterator* NameTable::Iterator() {
+  Ptr<NameEntryIterator> output = new NameTable::NameEntryIterator(this);
+  return output.Detach();
+}
+
+CALLER_ATTACH
+NameTable::NameEntryIterator* NameTable::Iterator(NameEntryFilter* filter) {
+  Ptr<NameEntryIterator> output =
+      new NameTable::NameEntryIterator(this, filter);
+  return output.Detach();
+}
+
+NameTable::NameTable(Header* header, ReadableFontData* data)
+    : SubTableContainerTable(header, data) {}
+
+int32_t NameTable::StringOffset() {
+  return data_->ReadUShort(Offset::kStringOffset);
+}
+
+int32_t NameTable::OffsetForNameRecord(int32_t index) {
+  return Offset::kNameRecordStart + index * Offset::kNameRecordSize;
+}
+
+int32_t NameTable::NameLength(int32_t index) {
+  return data_->ReadUShort(Offset::kNameRecordStringLength +
+                           OffsetForNameRecord(index));
+}
+
+int32_t NameTable::NameOffset(int32_t index) {
+  return data_->ReadUShort(Offset::kNameRecordStringOffset +
+                           OffsetForNameRecord(index)) + StringOffset();
+}
+
+const char* NameTable::GetEncodingName(int32_t platform_id,
+                                       int32_t encoding_id) {
+  switch (platform_id) {
+    case PlatformId::kUnicode:
+      return "UTF-16BE";
+    case PlatformId::kMacintosh:
+      switch (encoding_id) {
+        case MacintoshEncodingId::kRoman:
+          return "MacRoman";
+        case MacintoshEncodingId::kJapanese:
+          return "Shift-JIS";
+        case MacintoshEncodingId::kChineseTraditional:
+          return "Big5";
+        case MacintoshEncodingId::kKorean:
+          return "EUC-KR";
+        case MacintoshEncodingId::kArabic:
+          return "MacArabic";
+        case MacintoshEncodingId::kHebrew:
+          return "MacHebrew";
+        case MacintoshEncodingId::kGreek:
+          return "MacGreek";
+        case MacintoshEncodingId::kRussian:
+          return "MacCyrillic";
+        case MacintoshEncodingId::kRSymbol:
+          return "MacSymbol";
+        case MacintoshEncodingId::kThai:
+          return "MacThai";
+        case MacintoshEncodingId::kChineseSimplified:
+          return "EUC-CN";
+        default:  // Note: unknown/unconfirmed cases are not ported.
+          break;
+      }
+      break;
+    case PlatformId::kISO:
+      break;
+    case PlatformId::kWindows:
+      switch (encoding_id) {
+        case WindowsEncodingId::kSymbol:
+        case WindowsEncodingId::kUnicodeUCS2:
+          return "UTF-16BE";
+        case WindowsEncodingId::kShiftJIS:
+          return "windows-933";
+        case WindowsEncodingId::kPRC:
+          return "windows-936";
+        case WindowsEncodingId::kBig5:
+          return "windows-950";
+        case WindowsEncodingId::kWansung:
+          return "windows-949";
+        case WindowsEncodingId::kJohab:
+          return "ms1361";
+        case WindowsEncodingId::kUnicodeUCS4:
+          return "UCS-4";
+      }
+      break;
+    case PlatformId::kCustom:
+      break;
+    default:
+      break;
+  }
+  return NULL;
+}
+
+UConverter* NameTable::GetCharset(int32_t platform_id, int32_t encoding_id) {
+  UErrorCode error_code = U_ZERO_ERROR;
+  UConverter* conv = ucnv_open(GetEncodingName(platform_id, encoding_id),
+                               &error_code);
+  if (U_SUCCESS(error_code)) {
+    return conv;
+  }
+
+  if (conv) {
+    ucnv_close(conv);
+  }
+  return NULL;
+}
+
+void NameTable::ConvertToNameBytes(const UChar* name,
+                                   int32_t platform_id,
+                                   int32_t encoding_id,
+                                   ByteVector* b) {
+  assert(b);
+  assert(name);
+  b->clear();
+  UConverter* cs = GetCharset(platform_id, encoding_id);
+  if (cs == NULL) {
+    return;
+  }
+
+  // Preflight to get buffer size.
+  UErrorCode error_code = U_ZERO_ERROR;
+  int32_t length = ucnv_fromUChars(cs, NULL, 0, name, -1, &error_code);
+  b->resize(length + 4);  // The longest termination "\0" is 4 bytes.
+  memset(&((*b)[0]), 0, length + 4);
+  error_code = U_ZERO_ERROR;
+  ucnv_fromUChars(cs,
+                  reinterpret_cast<char*>(&((*b)[0])),
+                  length + 4,
+                  name,
+                  -1,
+                  &error_code);
+  if (!U_SUCCESS(error_code)) {
+    b->clear();
+  }
+  ucnv_close(cs);
+}
+
+UChar* NameTable::ConvertFromNameBytes(ByteVector* name_bytes,
+                                       int32_t platform_id,
+                                       int32_t encoding_id) {
+  if (name_bytes == NULL || name_bytes->size() == 0) {
+    return NULL;
+  }
+  UConverter* cs = GetCharset(platform_id, encoding_id);
+  UErrorCode error_code = U_ZERO_ERROR;
+  if (cs == NULL) {
+    char buffer[11] = {0};
+#if defined (WIN32)
+    _itoa_s(platform_id, buffer, 16);
+#else
+    snprintf(buffer, sizeof(buffer), "%x", platform_id);
+#endif
+    UChar* result = new UChar[12];
+    memset(result, 0, sizeof(UChar) * 12);
+    cs = ucnv_open("utf-8", &error_code);
+    if (U_SUCCESS(error_code)) {
+      ucnv_toUChars(cs, result, 12, buffer, 11, &error_code);
+      ucnv_close(cs);
+      if (U_SUCCESS(error_code)) {
+        return result;
+      }
+    }
+    delete[] result;
+    return NULL;
+  }
+
+  // No preflight needed here, we will be bigger.
+  UChar* output_buffer = new UChar[name_bytes->size() + 1];
+  memset(output_buffer, 0, sizeof(UChar) * (name_bytes->size() + 1));
+  int32_t length = ucnv_toUChars(cs,
+                                 output_buffer,
+                                 name_bytes->size(),
+                                 reinterpret_cast<char*>(&((*name_bytes)[0])),
+                                 name_bytes->size(),
+                                 &error_code);
+  ucnv_close(cs);
+  if (length > 0) {
+    return output_buffer;
+  }
+
+  delete[] output_buffer;
+  return NULL;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/name_table.h b/sfntly/cpp/src/sfntly/table/core/name_table.h
new file mode 100644
index 0000000..4eaafbb
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/name_table.h
@@ -0,0 +1,743 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_NAME_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_NAME_TABLE_H_
+
+// Must include this before ICU to avoid stdint redefinition issue.
+#include "sfntly/port/type.h"
+
+#include <unicode/ucnv.h>
+#include <unicode/ustring.h>
+
+#include <map>
+#include <utility>
+
+#include "sfntly/port/java_iterator.h"
+#include "sfntly/table/subtable_container_table.h"
+
+namespace sfntly {
+
+// The following code implements the name table defined in TTF/OTF spec, which
+// can be found at http://www.microsoft.com/typography/otspec/name.htm.
+
+// Name IDs defined in TTF/OTF spec.
+struct NameId {
+  enum {
+    kUnknown = -1,
+    kCopyrightNotice = 0,
+    kFontFamilyName = 1,
+    kFontSubfamilyName = 2,
+    kUniqueFontIdentifier = 3,
+    kFullFontName = 4,
+    kVersionString = 5,
+    kPostscriptName = 6,
+    kTrademark = 7,
+    kManufacturerName = 8,
+    kDesigner = 9,
+    kDescription = 10,
+    kVendorURL = 11,
+    kDesignerURL = 12,
+    kLicenseDescription = 13,
+    kLicenseInfoURL = 14,
+    kReserved15 = 15,
+    kPreferredFamily = 16,
+    kPreferredSubfamily = 17,
+    kCompatibleFullName = 18,
+    kSampleText = 19,
+    kPostscriptCID = 20,
+    kWWSFamilyName = 21,
+    kWWSSubfamilyName = 22
+  };
+};
+
+// Unicode language IDs used in Name Records.
+struct UnicodeLanguageId {
+  enum {
+    kUnknown = -1,
+    kAll = 0
+  };
+};
+
+// Macintosh Language IDs (platform ID = 1)
+struct MacintoshLanguageId {
+  enum {
+    kUnknown = -1,
+    kEnglish = 0,
+    kFrench = 1,
+    kGerman = 2,
+    kItalian = 3,
+    kDutch = 4,
+    kSwedish = 5,
+    kSpanish = 6,
+    kDanish = 7,
+    kPortuguese = 8,
+    kNorwegian = 9,
+    kHebrew = 10,
+    kJapanese = 11,
+    kArabic = 12,
+    kFinnish = 13,
+    kGreek = 14,
+    kIcelandic = 15,
+    kMaltese = 16,
+    kTurkish = 17,
+    kCroatian = 18,
+    kChinese_Traditional = 19,
+    kUrdu = 20,
+    kHindi = 21,
+    kThai = 22,
+    kKorean = 23,
+    kLithuanian = 24,
+    kPolish = 25,
+    kHungarian = 26,
+    kEstonian = 27,
+    kLatvian = 28,
+    kSami = 29,
+    kFaroese = 30,
+    kFarsiPersian = 31,
+    kRussian = 32,
+    kChinese_Simplified = 33,
+    kFlemish = 34,
+    kIrishGaelic = 35,
+    kAlbanian = 36,
+    kRomanian = 37,
+    kCzech = 38,
+    kSlovak = 39,
+    kSlovenian = 40,
+    kYiddish = 41,
+    kSerbian = 42,
+    kMacedonian = 43,
+    kBulgarian = 44,
+    kUkrainian = 45,
+    kByelorussian = 46,
+    kUzbek = 47,
+    kKazakh = 48,
+    kAzerbaijani_Cyrillic = 49,
+    kAzerbaijani_Arabic = 50,
+    kArmenian = 51,
+    kGeorgian = 52,
+    kMoldavian = 53,
+    kKirghiz = 54,
+    kTajiki = 55,
+    kTurkmen = 56,
+    kMongolian_Mongolian = 57,
+    kMongolian_Cyrillic = 58,
+    kPashto = 59,
+    kKurdish = 60,
+    kKashmiri = 61,
+    kSindhi = 62,
+    kTibetan = 63,
+    kNepali = 64,
+    kSanskrit = 65,
+    kMarathi = 66,
+    kBengali = 67,
+    kAssamese = 68,
+    kGujarati = 69,
+    kPunjabi = 70,
+    kOriya = 71,
+    kMalayalam = 72,
+    kKannada = 73,
+    kTamil = 74,
+    kTelugu = 75,
+    kSinhalese = 76,
+    kBurmese = 77,
+    kKhmer = 78,
+    kLao = 79,
+    kVietnamese = 80,
+    kIndonesian = 81,
+    kTagalong = 82,
+    kMalay_Roman = 83,
+    kMalay_Arabic = 84,
+    kAmharic = 85,
+    kTigrinya = 86,
+    kGalla = 87,
+    kSomali = 88,
+    kSwahili = 89,
+    kKinyarwandaRuanda = 90,
+    kRundi = 91,
+    kNyanjaChewa = 92,
+    kMalagasy = 93,
+    kEsperanto = 94,
+    kWelsh = 128,
+    kBasque = 129,
+    kCatalan = 130,
+    kLatin = 131,
+    kQuenchua = 132,
+    kGuarani = 133,
+    kAymara = 134,
+    kTatar = 135,
+    kUighur = 136,
+    kDzongkha = 137,
+    kJavanese_Roman = 138,
+    kSundanese_Roman = 139,
+    kGalician = 140,
+    kAfrikaans = 141,
+    kBreton = 142,
+    kInuktitut = 143,
+    kScottishGaelic = 144,
+    kManxGaelic = 145,
+    kIrishGaelic_WithDotAbove = 146,
+    kTongan = 147,
+    kGreek_Polytonic = 148,
+    kGreenlandic = 149,
+    kAzerbaijani_Roman = 150
+  };
+};
+
+// Windows Language IDs (platformID = 3)
+struct WindowsLanguageId {
+  enum {
+    kUnknown = -1,
+    kAfrikaans_SouthAfrica = 0x0436,
+    kAlbanian_Albania = 0x041C,
+    kAlsatian_France = 0x0484,
+    kAmharic_Ethiopia = 0x045E,
+    kArabic_Algeria = 0x1401,
+    kArabic_Bahrain = 0x3C01,
+    kArabic_Egypt = 0x0C01,
+    kArabic_Iraq = 0x0801,
+    kArabic_Jordan = 0x2C01,
+    kArabic_Kuwait = 0x3401,
+    kArabic_Lebanon = 0x3001,
+    kArabic_Libya = 0x1001,
+    kArabic_Morocco = 0x1801,
+    kArabic_Oman = 0x2001,
+    kArabic_Qatar = 0x4001,
+    kArabic_SaudiArabia = 0x0401,
+    kArabic_Syria = 0x2801,
+    kArabic_Tunisia = 0x1C01,
+    kArabic_UAE = 0x3801,
+    kArabic_Yemen = 0x2401,
+    kArmenian_Armenia = 0x042B,
+    kAssamese_India = 0x044D,
+    kAzeri_Cyrillic_Azerbaijan = 0x082C,
+    kAzeri_Latin_Azerbaijan = 0x042C,
+    kBashkir_Russia = 0x046D,
+    kBasque_Basque = 0x042D,
+    kBelarusian_Belarus = 0x0423,
+    kBengali_Bangladesh = 0x0845,
+    kBengali_India = 0x0445,
+    kBosnian_Cyrillic_BosniaAndHerzegovina = 0x201A,
+    kBosnian_Latin_BosniaAndHerzegovina = 0x141A,
+    kBreton_France = 0x047E,
+    kBulgarian_Bulgaria = 0x0402,
+    kCatalan_Catalan = 0x0403,
+    kChinese_HongKongSAR = 0x0C04,
+    kChinese_MacaoSAR = 0x1404,
+    kChinese_PeoplesRepublicOfChina = 0x0804,
+    kChinese_Singapore = 0x1004,
+    kChinese_Taiwan = 0x0404,
+    kCorsican_France = 0x0483,
+    kCroatian_Croatia = 0x041A,
+    kCroatian_Latin_BosniaAndHerzegovina = 0x101A,
+    kCzech_CzechRepublic = 0x0405,
+    kDanish_Denmark = 0x0406,
+    kDari_Afghanistan = 0x048C,
+    kDivehi_Maldives = 0x0465,
+    kDutch_Belgium = 0x0813,
+    kDutch_Netherlands = 0x0413,
+    kEnglish_Australia = 0x0C09,
+    kEnglish_Belize = 0x2809,
+    kEnglish_Canada = 0x1009,
+    kEnglish_Caribbean = 0x2409,
+    kEnglish_India = 0x4009,
+    kEnglish_Ireland = 0x1809,
+    kEnglish_Jamaica = 0x2009,
+    kEnglish_Malaysia = 0x4409,
+    kEnglish_NewZealand = 0x1409,
+    kEnglish_RepublicOfThePhilippines = 0x3409,
+    kEnglish_Singapore = 0x4809,
+    kEnglish_SouthAfrica = 0x1C09,
+    kEnglish_TrinidadAndTobago = 0x2C09,
+    kEnglish_UnitedKingdom = 0x0809,
+    kEnglish_UnitedStates = 0x0409,
+    kEnglish_Zimbabwe = 0x3009,
+    kEstonian_Estonia = 0x0425,
+    kFaroese_FaroeIslands = 0x0438,
+    kFilipino_Philippines = 0x0464,
+    kFinnish_Finland = 0x040B,
+    kFrench_Belgium = 0x080C,
+    kFrench_Canada = 0x0C0C,
+    kFrench_France = 0x040C,
+    kFrench_Luxembourg = 0x140c,
+    kFrench_PrincipalityOfMonoco = 0x180C,
+    kFrench_Switzerland = 0x100C,
+    kFrisian_Netherlands = 0x0462,
+    kGalician_Galician = 0x0456,
+    kGeorgian_Georgia = 0x0437,
+    kGerman_Austria = 0x0C07,
+    kGerman_Germany = 0x0407,
+    kGerman_Liechtenstein = 0x1407,
+    kGerman_Luxembourg = 0x1007,
+    kGerman_Switzerland = 0x0807,
+    kGreek_Greece = 0x0408,
+    kGreenlandic_Greenland = 0x046F,
+    kGujarati_India = 0x0447,
+    kHausa_Latin_Nigeria = 0x0468,
+    kHebrew_Israel = 0x040D,
+    kHindi_India = 0x0439,
+    kHungarian_Hungary = 0x040E,
+    kIcelandic_Iceland = 0x040F,
+    kIgbo_Nigeria = 0x0470,
+    kIndonesian_Indonesia = 0x0421,
+    kInuktitut_Canada = 0x045D,
+    kInuktitut_Latin_Canada = 0x085D,
+    kIrish_Ireland = 0x083C,
+    kisiXhosa_SouthAfrica = 0x0434,
+    kisiZulu_SouthAfrica = 0x0435,
+    kItalian_Italy = 0x0410,
+    kItalian_Switzerland = 0x0810,
+    kJapanese_Japan = 0x0411,
+    kKannada_India = 0x044B,
+    kKazakh_Kazakhstan = 0x043F,
+    kKhmer_Cambodia = 0x0453,
+    kKiche_Guatemala = 0x0486,
+    kKinyarwanda_Rwanda = 0x0487,
+    kKiswahili_Kenya = 0x0441,
+    kKonkani_India = 0x0457,
+    kKorean_Korea = 0x0412,
+    kKyrgyz_Kyrgyzstan = 0x0440,
+    kLao_LaoPDR = 0x0454,
+    kLatvian_Latvia = 0x0426,
+    kLithuanian_Lithuania = 0x0427,
+    kLowerSorbian_Germany = 0x082E,
+    kLuxembourgish_Luxembourg = 0x046E,
+    kMacedonian_FYROM_FormerYugoslavRepublicOfMacedonia = 0x042F,
+    kMalay_BruneiDarussalam = 0x083E,
+    kMalay_Malaysia = 0x043E,
+    kMalayalam_India = 0x044C,
+    kMaltese_Malta = 0x043A,
+    kMaori_NewZealand = 0x0481,
+    kMapudungun_Chile = 0x047A,
+    kMarathi_India = 0x044E,
+    kMohawk_Mohawk = 0x047C,
+    kMongolian_Cyrillic_Mongolia = 0x0450,
+    kMongolian_Traditional_PeoplesRepublicOfChina = 0x0850,
+    kNepali_Nepal = 0x0461,
+    kNorwegian_Bokmal_Norway = 0x0414,
+    kNorwegian_Nynorsk_Norway = 0x0814,
+    kOccitan_France = 0x0482,
+    kOriya_India = 0x0448,
+    kPashto_Afghanistan = 0x0463,
+    kPolish_Poland = 0x0415,
+    kPortuguese_Brazil = 0x0416,
+    kPortuguese_Portugal = 0x0816,
+    kPunjabi_India = 0x0446,
+    kQuechua_Bolivia = 0x046B,
+    kQuechua_Ecuador = 0x086B,
+    kQuechua_Peru = 0x0C6B,
+    kRomanian_Romania = 0x0418,
+    kRomansh_Switzerland = 0x0417,
+    kRussian_Russia = 0x0419,
+    kSami_Inari_Finland = 0x243B,
+    kSami_Lule_Norway = 0x103B,
+    kSami_Lule_Sweden = 0x143B,
+    kSami_Northern_Finland = 0x0C3B,
+    kSami_Northern_Norway = 0x043B,
+    kSami_Northern_Sweden = 0x083B,
+    kSami_Skolt_Finland = 0x203B,
+    kSami_Southern_Norway = 0x183B,
+    kSami_Southern_Sweden = 0x1C3B,
+    kSanskrit_India = 0x044F,
+    kSerbian_Cyrillic_BosniaAndHerzegovina = 0x1C1A,
+    kSerbian_Cyrillic_Serbia = 0x0C1A,
+    kSerbian_Latin_BosniaAndHerzegovina = 0x181A,
+    kSerbian_Latin_Serbia = 0x081A,
+    kSesothoSaLeboa_SouthAfrica = 0x046C,
+    kSetswana_SouthAfrica = 0x0432,
+    kSinhala_SriLanka = 0x045B,
+    kSlovak_Slovakia = 0x041B,
+    kSlovenian_Slovenia = 0x0424,
+    kSpanish_Argentina = 0x2C0A,
+    kSpanish_Bolivia = 0x400A,
+    kSpanish_Chile = 0x340A,
+    kSpanish_Colombia = 0x240A,
+    kSpanish_CostaRica = 0x140A,
+    kSpanish_DominicanRepublic = 0x1C0A,
+    kSpanish_Ecuador = 0x300A,
+    kSpanish_ElSalvador = 0x440A,
+    kSpanish_Guatemala = 0x100A,
+    kSpanish_Honduras = 0x480A,
+    kSpanish_Mexico = 0x080A,
+    kSpanish_Nicaragua = 0x4C0A,
+    kSpanish_Panama = 0x180A,
+    kSpanish_Paraguay = 0x3C0A,
+    kSpanish_Peru = 0x280A,
+    kSpanish_PuertoRico = 0x500A,
+    kSpanish_ModernSort_Spain = 0x0C0A,
+    kSpanish_TraditionalSort_Spain = 0x040A,
+    kSpanish_UnitedStates = 0x540A,
+    kSpanish_Uruguay = 0x380A,
+    kSpanish_Venezuela = 0x200A,
+    kSweden_Finland = 0x081D,
+    kSwedish_Sweden = 0x041D,
+    kSyriac_Syria = 0x045A,
+    kTajik_Cyrillic_Tajikistan = 0x0428,
+    kTamazight_Latin_Algeria = 0x085F,
+    kTamil_India = 0x0449,
+    kTatar_Russia = 0x0444,
+    kTelugu_India = 0x044A,
+    kThai_Thailand = 0x041E,
+    kTibetan_PRC = 0x0451,
+    kTurkish_Turkey = 0x041F,
+    kTurkmen_Turkmenistan = 0x0442,
+    kUighur_PRC = 0x0480,
+    kUkrainian_Ukraine = 0x0422,
+    kUpperSorbian_Germany = 0x042E,
+    kUrdu_IslamicRepublicOfPakistan = 0x0420,
+    kUzbek_Cyrillic_Uzbekistan = 0x0843,
+    kUzbek_Latin_Uzbekistan = 0x0443,
+    kVietnamese_Vietnam = 0x042A,
+    kWelsh_UnitedKingdom = 0x0452,
+    kWolof_Senegal = 0x0448,
+    kYakut_Russia = 0x0485,
+    kYi_PRC = 0x0478,
+    kYoruba_Nigeria = 0x046A
+  };
+};
+
+class NameTable : public SubTableContainerTable, public RefCounted<NameTable> {
+ public:
+  // Unique identifier for a given name record.
+  class NameEntryId {
+   public:
+    NameEntryId();  // C++ port only, must provide default constructor.
+    NameEntryId(int32_t platform_id, int32_t encoding_id, int32_t language_id,
+                int32_t name_id);
+    NameEntryId(const NameEntryId&);
+    // Make gcc -Wnon-virtual-dtor happy.
+    virtual ~NameEntryId() {}
+
+    int32_t platform_id() const { return platform_id_; }
+    int32_t encoding_id() const { return encoding_id_; }
+    int32_t language_id() const { return language_id_; }
+    int32_t name_id() const { return name_id_; }
+
+    const NameEntryId& operator=(const NameEntryId& rhs) const;
+    bool operator==(const NameEntryId& rhs) const;
+    bool operator<(const NameEntryId& rhs) const;
+
+    // UNIMPLEMENTED: int hashCode()
+    //                String toString()
+
+   private:
+    mutable int32_t platform_id_;
+    mutable int32_t encoding_id_;
+    mutable int32_t language_id_;
+    mutable int32_t name_id_;
+  };
+
+  class NameEntryBuilder;
+
+  // Class to represent a name entry in the name table.
+  class NameEntry : public RefCounted<NameEntry> {
+   public:
+    NameEntry();
+    NameEntry(const NameEntryId& name_entry_id, const ByteVector& name_bytes);
+    NameEntry(int32_t platform_id,
+              int32_t encoding_id,
+              int32_t language_id,
+              int32_t name_id,
+              const ByteVector& name_bytes);
+    virtual ~NameEntry();
+
+    NameEntryId& name_entry_id() { return name_entry_id_; }
+    int32_t platform_id() const { return name_entry_id_.platform_id(); }
+    int32_t encoding_id() const { return name_entry_id_.encoding_id(); }
+    int32_t language_id() const { return name_entry_id_.language_id(); }
+    int32_t name_id() const { return name_entry_id_.name_id(); }
+
+    // Get the bytes for name.  Returned pointer is the address of private
+    // member of this class, do not attempt to delete.
+    ByteVector* NameAsBytes();
+
+    // C++ port only: get the length of NameAsBytes.
+    int32_t NameBytesLength();
+
+    // Returns the name in Unicode as UChar array.
+    // Note: ICU UChar* convention requires caller to delete[] it.
+    UChar* Name();
+    bool operator==(const NameEntry& rhs) const;
+
+    // UNIMPLEMENTED: String toString()
+    //                int hashCode()
+
+   private:
+    void Init(int32_t platform_id, int32_t encoding_id, int32_t language_id,
+              int32_t name_id, const ByteVector* name_bytes);
+
+    NameEntryId name_entry_id_;
+    ByteVector name_bytes_;
+
+    friend class NameEntryBuilder;
+  };
+
+  // Builder of a name entry.
+  // C++ port: original Java hierarchy inherits from NameEntry.  In C++ port, we
+  // opted not doing so to avoid ref count issues and nasty protected members.
+  class NameEntryBuilder : public RefCounted<NameEntryBuilder> {
+   public:
+    NameEntryBuilder();
+    NameEntryBuilder(const NameEntryId& name_entry_id,
+                     const ByteVector& name_bytes);
+    explicit NameEntryBuilder(const NameEntryId& name_entry_id);
+    explicit NameEntryBuilder(NameEntry* entry);
+    virtual ~NameEntryBuilder();
+
+    virtual void SetName(const UChar* name);
+    virtual void SetName(const ByteVector& name_bytes);
+    virtual void SetName(const ByteVector& name_bytes,
+                         int32_t offset,
+                         int32_t length);
+
+    // C++ port only. CALLER_ATTACH is not added because the lifetime shall be
+    // controlled by this class, therefore the caller shall not increase the ref
+    // count.
+    NameEntry* name_entry() { return name_entry_; }
+
+   private:
+    void Init(int32_t platform_id, int32_t encoding_id, int32_t language_id,
+              int32_t name_id, const ByteVector* name_bytes);
+
+    Ptr<NameEntry> name_entry_;
+  };
+  typedef std::map<NameEntryId, Ptr<NameEntryBuilder> > NameEntryBuilderMap;
+
+  // An interface for a filter to use with the name entry iterator. This allows
+  // name entries to be iterated and only those acceptable to the filter will be
+  // returned.
+  class NameEntryFilter {
+   public:
+    virtual bool Accept(int32_t platform_id,
+                        int32_t encoding_id,
+                        int32_t language_id,
+                        int32_t name_id) = 0;
+    // Make gcc -Wnon-virtual-dtor happy.
+    virtual ~NameEntryFilter() {}
+  };
+
+  // C++ port only: an in-place filter to mimic Java Iterator's filtering.
+  class NameEntryFilterInPlace : public NameEntryFilter {
+   public:
+    NameEntryFilterInPlace(int32_t platform_id,
+                           int32_t encoding_id,
+                           int32_t language_id,
+                           int32_t name_id);
+    // Make gcc -Wnon-virtual-dtor happy.
+    virtual ~NameEntryFilterInPlace() {}
+
+    virtual bool Accept(int32_t platform_id,
+                        int32_t encoding_id,
+                        int32_t language_id,
+                        int32_t name_id);
+
+   private:
+    int32_t platform_id_;
+    int32_t encoding_id_;
+    int32_t language_id_;
+    int32_t name_id_;
+  };
+
+  class NameEntryIterator : public RefIterator<NameEntry, NameTable> {
+   public:
+    // If filter is NULL, filter through all tables.
+    explicit NameEntryIterator(NameTable* table);
+    NameEntryIterator(NameTable* table, NameEntryFilter* filter);
+    virtual ~NameEntryIterator() {}
+
+    virtual bool HasNext();
+    virtual CALLER_ATTACH NameEntry* Next();
+
+   private:
+    int32_t name_index_;
+    NameEntryFilter* filter_;
+  };
+
+  // The builder to construct name table for outputting.
+  class Builder : public SubTableContainerTable::Builder,
+                  public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public because C++ does not allow base
+    // class to instantiate derived class with protected constructors.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    // Revert the name builders for the name table to the last version that came
+    // from data.
+    void RevertNames();
+
+    // Number of name entry builders contained.
+    int32_t BuilderCount();
+
+    // Note: For C++ port, clear() is not implemented.  The clear() function
+    //       implies completely remove name entry builders, which is easy in
+    //       Java but will take a lot of efforts in C++ to release the builders
+    //       nicely and correctly.
+    // TODO(arthurhsu): IMPLEMENT
+    // Clear the name builders for the name table.
+    // void clear();
+
+    // Check the existance of a name entry builder by key.
+    bool Has(int32_t platform_id, int32_t encoding_id, int32_t language_id,
+             int32_t name_id);
+
+    // Get name entry builder by key.
+    CALLER_ATTACH NameEntryBuilder* NameBuilder(int32_t platform_id,
+        int32_t encoding_id, int32_t language_id, int32_t name_id);
+
+    // Remove name entry builder by key.
+    bool Remove(int32_t platform_id, int32_t encoding_id, int32_t language_id,
+                int32_t name_id);
+
+    // FontDataTable::Builder API implementation
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+   private:
+    void Initialize(ReadableFontData* data);
+    NameEntryBuilderMap* GetNameBuilders();
+
+    // Note: callers should use the getter funtion provided above to ensure that
+    // this is lazily initialized instead of accessing directly.
+    NameEntryBuilderMap name_entry_map_;
+  };
+
+  /****************************************************************************
+   * public methods of NameTable class
+   ****************************************************************************/
+  virtual ~NameTable();
+
+  // Get the format used in the name table.
+  virtual int32_t Format();
+
+  // Get the number of names in the name table.
+  virtual int32_t NameCount();
+
+  // Get the platform id for the given name record.
+  virtual int32_t PlatformId(int32_t index);
+
+  // Get the encoding id for the given name record.
+  // see MacintoshEncodingId, WindowsEncodingId, UnicodeEncodingId
+  virtual int32_t EncodingId(int32_t index);
+
+  // Get the language id for the given name record.
+  virtual int32_t LanguageId(int32_t index);
+
+  // Get the name id for given name record.
+  virtual int32_t NameId(int32_t index);
+
+  // Get the name as bytes for the specified name. If there is no entry for the
+  // requested name, then empty vector is returned.
+  virtual void NameAsBytes(int32_t index, ByteVector* b);
+  virtual void NameAsBytes(int32_t platform_id, int32_t encoding_id,
+                           int32_t language_id, int32_t name_id,
+                           ByteVector* b);
+
+  // Get the name as a UChar* for the given name record. If there is no
+  // encoding conversion available for the name record then a best attempt
+  // UChar* will be returned.
+  // Note: ICU UChar* convention requires caller to delete[] it.
+  virtual UChar* Name(int32_t index);
+
+  // Get the name as a UChar* for the specified name. If there is no entry for
+  // the requested name then NULL is returned. If there is no encoding
+  // conversion available for the name then a best attempt UChar* will be
+  // returned.
+  // Note: ICU UChar* convention requires caller to delete[] it.
+  virtual UChar* Name(int32_t platform_id, int32_t encoding_id,
+                      int32_t language_id, int32_t name_id);
+
+  // Note: These functions are renamed in C++ port.  Their original Java name is
+  // nameEntry().
+  virtual CALLER_ATTACH NameEntry* GetNameEntry(int32_t index);
+  virtual CALLER_ATTACH NameEntry* GetNameEntry(int32_t platform_id,
+      int32_t encoding_id, int32_t language_id, int32_t name_id);
+
+  // Note: Not implemented in C++ port due to complexity and low usage.
+  // virtual void names(std::set<NameEntryPtr>*);
+
+  // Get the iterator to iterate through all name entries.
+  virtual CALLER_ATTACH NameEntryIterator* Iterator();
+  virtual CALLER_ATTACH NameEntryIterator* Iterator(NameEntryFilter* filter);
+
+ private:
+  struct Offset {
+    enum {
+      kFormat = 0,
+      kCount = 2,
+      kStringOffset = 4,
+      kNameRecordStart = 6,
+
+      // Format 1 - offset from the end of the name records
+      kLangTagCount = 0,
+      kLangTagRecord = 2,
+
+      kNameRecordSize = 12,
+      // Name Records
+      kNameRecordPlatformId = 0,
+      kNameRecordEncodingId = 2,
+      kNameRecordLanguageId = 4,
+      kNameRecordNameId = 6,
+      kNameRecordStringLength = 8,
+      kNameRecordStringOffset = 10
+    };
+  };
+
+  // The table shall be constructed using Builder, no direct instantiation.
+  NameTable(Header* header, ReadableFontData* data);
+
+  // Get the offset to the string data in the name table.
+  int32_t StringOffset();
+
+  // Get the offset for the given name record.
+  int32_t OffsetForNameRecord(int32_t index);
+
+  // Get the length of the string data for the given name record.
+  int32_t NameLength(int32_t index);
+
+  // Get the offset of the string data for the given name record.
+  int32_t NameOffset(int32_t index);
+
+  // Note: string literals are returned.  Caller shall not attempt to manipulate
+  // the returned pointer.
+  static const char* GetEncodingName(int32_t platform_id, int32_t encoding_id);
+
+  // Note: ICU UConverter* convention requires caller to ucnv_close() it.
+  static UConverter* GetCharset(int32_t platform_id, int32_t encoding_id);
+
+  // Note: Output will be stored in ByteVector* b.  Original data in b will be
+  // erased and replaced with converted name bytes.
+  static void ConvertToNameBytes(const UChar* name, int32_t platform_id,
+                                 int32_t encoding_id, ByteVector* b);
+
+  // Note: ICU UChar* convention requires caller to delete[] it.
+  static UChar* ConvertFromNameBytes(ByteVector* name_bytes,
+                                     int32_t platform_id, int32_t encoding_id);
+};  // class NameTable
+typedef Ptr<NameTable> NameTablePtr;
+typedef Ptr<NameTable::NameEntry> NameEntryPtr;
+typedef Ptr<NameTable::Builder> NameTableBuilderPtr;
+typedef Ptr<NameTable::NameEntryBuilder> NameEntryBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_NAME_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/core/os2_table.cc b/sfntly/cpp/src/sfntly/table/core/os2_table.cc
new file mode 100644
index 0000000..7ca9d9a
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/os2_table.cc
@@ -0,0 +1,608 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/core/os2_table.h"
+
+namespace sfntly {
+/******************************************************************************
+ * Constants
+ ******************************************************************************/
+const int64_t CodePageRange::kLatin1_1252 = (int64_t)1 << 0;
+const int64_t CodePageRange::kLatin2_1250 = (int64_t)1 << (int64_t)1;
+const int64_t CodePageRange::kCyrillic_1251 = (int64_t)1 << 2;
+const int64_t CodePageRange::kGreek_1253 = (int64_t)1 << 3;
+const int64_t CodePageRange::kTurkish_1254 = (int64_t)1 << 4;
+const int64_t CodePageRange::kHebrew_1255 = (int64_t)1 << 5;
+const int64_t CodePageRange::kArabic_1256 = (int64_t)1 << 6;
+const int64_t CodePageRange::kWindowsBaltic_1257 = (int64_t)1 << 7;
+const int64_t CodePageRange::kVietnamese_1258 = (int64_t)1 << 8;
+const int64_t CodePageRange::kAlternateANSI9 = (int64_t)1 << 9;
+const int64_t CodePageRange::kAlternateANSI10 = (int64_t)1 << 10;
+const int64_t CodePageRange::kAlternateANSI11 = (int64_t)1 << 11;
+const int64_t CodePageRange::kAlternateANSI12 = (int64_t)1 << 12;
+const int64_t CodePageRange::kAlternateANSI13 = (int64_t)1 << 13;
+const int64_t CodePageRange::kAlternateANSI14 = (int64_t)1 << 14;
+const int64_t CodePageRange::kAlternateANSI15 = (int64_t)1 << 15;
+const int64_t CodePageRange::kThai_874 = (int64_t)1 << 16;
+const int64_t CodePageRange::kJapanJIS_932 = (int64_t)1 << 17;
+const int64_t CodePageRange::kChineseSimplified_936 = (int64_t)1 << 18;
+const int64_t CodePageRange::kKoreanWansung_949 = (int64_t)1 << 19;
+const int64_t CodePageRange::kChineseTraditional_950 = (int64_t)1 << 20;
+const int64_t CodePageRange::kKoreanJohab_1361 = (int64_t)1 << 21;
+const int64_t CodePageRange::kAlternateANSI22 = (int64_t)1 << 22;
+const int64_t CodePageRange::kAlternateANSI23 = (int64_t)1 << 23;
+const int64_t CodePageRange::kAlternateANSI24 = (int64_t)1 << 24;
+const int64_t CodePageRange::kAlternateANSI25 = (int64_t)1 << 25;
+const int64_t CodePageRange::kAlternateANSI26 = (int64_t)1 << 26;
+const int64_t CodePageRange::kAlternateANSI27 = (int64_t)1 << 27;
+const int64_t CodePageRange::kAlternateANSI28 = (int64_t)1 << 28;
+const int64_t CodePageRange::kMacintoshCharacterSet = (int64_t)1 << 29;
+const int64_t CodePageRange::kOEMCharacterSet = (int64_t)1 << 30;
+const int64_t CodePageRange::kSymbolCharacterSet = (int64_t)1 << 31;
+const int64_t CodePageRange::kReservedForOEM32 = (int64_t)1 << 32;
+const int64_t CodePageRange::kReservedForOEM33 = (int64_t)1 << 33;
+const int64_t CodePageRange::kReservedForOEM34 = (int64_t)1 << 34;
+const int64_t CodePageRange::kReservedForOEM35 = (int64_t)1 << 35;
+const int64_t CodePageRange::kReservedForOEM36 = (int64_t)1 << 36;
+const int64_t CodePageRange::kReservedForOEM37 = (int64_t)1 << 37;
+const int64_t CodePageRange::kReservedForOEM38 = (int64_t)1 << 38;
+const int64_t CodePageRange::kReservedForOEM39 = (int64_t)1 << 39;
+const int64_t CodePageRange::kReservedForOEM40 = (int64_t)1 << 40;
+const int64_t CodePageRange::kReservedForOEM41 = (int64_t)1 << 41;
+const int64_t CodePageRange::kReservedForOEM42 = (int64_t)1 << 42;
+const int64_t CodePageRange::kReservedForOEM43 = (int64_t)1 << 43;
+const int64_t CodePageRange::kReservedForOEM44 = (int64_t)1 << 44;
+const int64_t CodePageRange::kReservedForOEM45 = (int64_t)1 << 45;
+const int64_t CodePageRange::kReservedForOEM46 = (int64_t)1 << 46;
+const int64_t CodePageRange::kReservedForOEM47 = (int64_t)1 << 47;
+const int64_t CodePageRange::kIBMGreek_869 = (int64_t)1 << 48;
+const int64_t CodePageRange::kMSDOSRussion_866 = (int64_t)1 << 49;
+const int64_t CodePageRange::kMSDOSNordic_865 = (int64_t)1 << 50;
+const int64_t CodePageRange::kArabic_864 = (int64_t)1 << 51;
+const int64_t CodePageRange::kMSDOSCanadianFrench_863 = (int64_t)1 << 52;
+const int64_t CodePageRange::kHebrew_862 = (int64_t)1 << 53;
+const int64_t CodePageRange::kMSDOSIcelandic_861 = (int64_t)1 << 54;
+const int64_t CodePageRange::kMSDOSPortugese_860 = (int64_t)1 << 55;
+const int64_t CodePageRange::kIBMTurkish_857 = (int64_t)1 << 56;
+const int64_t CodePageRange::kIBMCyrillic_855 = (int64_t)1 << 57;
+const int64_t CodePageRange::kLatin2_852 = (int64_t)1 << 58;
+const int64_t CodePageRange::kMSDOSBaltic_775 = (int64_t)1 << 59;
+const int64_t CodePageRange::kGreek_737 = (int64_t)1 << 60;
+const int64_t CodePageRange::kArabic_708 = (int64_t)1 << 61;
+const int64_t CodePageRange::kLatin1_850 = (int64_t)1 << 62;
+const int64_t CodePageRange::kUS_437 = (int64_t)1 << 63;
+
+/******************************************************************************
+ * struct UnicodeRange
+ ******************************************************************************/
+int32_t UnicodeRange::range(int32_t bit) {
+  if (bit < 0 || bit > kLast) {
+    return -1;
+  }
+  return bit;
+}
+
+/******************************************************************************
+ * class OS2Table
+ ******************************************************************************/
+OS2Table::~OS2Table() {}
+
+int32_t OS2Table::TableVersion() {
+  return data_->ReadUShort(Offset::kVersion);
+}
+
+int32_t OS2Table::XAvgCharWidth() {
+  return data_->ReadShort(Offset::kXAvgCharWidth);
+}
+
+int32_t OS2Table::UsWeightClass() {
+  return data_->ReadUShort(Offset::kUsWeightClass);
+}
+
+int32_t OS2Table::UsWidthClass() {
+  return data_->ReadUShort(Offset::kUsWidthClass);
+}
+
+int32_t OS2Table::FsType() {
+  return data_->ReadUShort(Offset::kFsType);
+}
+
+int32_t OS2Table::YSubscriptXSize() {
+  return data_->ReadShort(Offset::kYSubscriptXSize);
+}
+
+int32_t OS2Table::YSubscriptYSize() {
+  return data_->ReadShort(Offset::kYSubscriptYSize);
+}
+
+int32_t OS2Table::YSubscriptXOffset() {
+  return data_->ReadShort(Offset::kYSubscriptXOffset);
+}
+
+int32_t OS2Table::YSubscriptYOffset() {
+  return data_->ReadShort(Offset::kYSubscriptYOffset);
+}
+
+int32_t OS2Table::YSuperscriptXSize() {
+  return data_->ReadShort(Offset::kYSuperscriptXSize);
+}
+
+int32_t OS2Table::YSuperscriptYSize() {
+  return data_->ReadShort(Offset::kYSuperscriptYSize);
+}
+
+int32_t OS2Table::YSuperscriptXOffset() {
+  return data_->ReadShort(Offset::kYSuperscriptXOffset);
+}
+
+int32_t OS2Table::YSuperscriptYOffset() {
+  return data_->ReadShort(Offset::kYSuperscriptYOffset);
+}
+
+int32_t OS2Table::YStrikeoutSize() {
+  return data_->ReadShort(Offset::kYStrikeoutSize);
+}
+
+int32_t OS2Table::YStrikeoutPosition() {
+  return data_->ReadShort(Offset::kYStrikeoutPosition);
+}
+
+int32_t OS2Table::SFamilyClass() {
+  return data_->ReadShort(Offset::kSFamilyClass);
+}
+
+void OS2Table::Panose(ByteVector* value) {
+  assert(value);
+  value->clear();
+  value->resize(10);
+  data_->ReadBytes(Offset::kPanose, &((*value)[0]), 0, 10);
+}
+
+int64_t OS2Table::UlUnicodeRange1() {
+  return data_->ReadULong(Offset::kUlUnicodeRange1);
+}
+
+int64_t OS2Table::UlUnicodeRange2() {
+  return data_->ReadULong(Offset::kUlUnicodeRange2);
+}
+
+int64_t OS2Table::UlUnicodeRange3() {
+  return data_->ReadULong(Offset::kUlUnicodeRange3);
+}
+
+int64_t OS2Table::UlUnicodeRange4() {
+  return data_->ReadULong(Offset::kUlUnicodeRange4);
+}
+
+void OS2Table::AchVendId(ByteVector* b) {
+  assert(b);
+  b->clear();
+  b->resize(4);
+  data_->ReadBytes(Offset::kAchVendId, &((*b)[0]), 0, 4);
+}
+
+int32_t OS2Table::FsSelection() {
+  return data_->ReadUShort(Offset::kFsSelection);
+}
+
+int32_t OS2Table::UsFirstCharIndex() {
+  return data_->ReadUShort(Offset::kUsFirstCharIndex);
+}
+
+int32_t OS2Table::UsLastCharIndex() {
+  return data_->ReadUShort(Offset::kUsLastCharIndex);
+}
+
+int32_t OS2Table::STypoAscender() {
+  return data_->ReadShort(Offset::kSTypoAscender);
+}
+
+int32_t OS2Table::STypoDescender() {
+  return data_->ReadShort(Offset::kSTypoDescender);
+}
+
+int32_t OS2Table::STypoLineGap() {
+  return data_->ReadShort(Offset::kSTypoLineGap);
+}
+
+int32_t OS2Table::UsWinAscent() {
+  return data_->ReadUShort(Offset::kUsWinAscent);
+}
+
+int32_t OS2Table::UsWinDescent() {
+  return data_->ReadUShort(Offset::kUsWinDescent);
+}
+
+int64_t OS2Table::UlCodePageRange1() {
+  return data_->ReadULong(Offset::kUlCodePageRange1);
+}
+
+int64_t OS2Table::UlCodePageRange2() {
+  return data_->ReadULong(Offset::kUlCodePageRange2);
+}
+
+int32_t OS2Table::SxHeight() {
+  return data_->ReadShort(Offset::kSxHeight);
+}
+
+int32_t OS2Table::SCapHeight() {
+  return data_->ReadShort(Offset::kSCapHeight);
+}
+
+int32_t OS2Table::UsDefaultChar() {
+  return data_->ReadUShort(Offset::kUsDefaultChar);
+}
+
+int32_t OS2Table::UsBreakChar() {
+  return data_->ReadUShort(Offset::kUsBreakChar);
+}
+
+int32_t OS2Table::UsMaxContext() {
+  return data_->ReadUShort(Offset::kUsMaxContext);
+}
+
+OS2Table::OS2Table(Header* header, ReadableFontData* data)
+    : Table(header, data) {
+}
+
+/******************************************************************************
+ * class OS2Table::Builder
+ ******************************************************************************/
+OS2Table::Builder::Builder(Header* header, WritableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+OS2Table::Builder::Builder(Header* header, ReadableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+OS2Table::Builder::~Builder() {}
+
+CALLER_ATTACH FontDataTable* OS2Table::Builder::SubBuildTable(
+    ReadableFontData* data) {
+  FontDataTablePtr table = new OS2Table(header(), data);
+  return table.Detach();
+}
+
+CALLER_ATTACH OS2Table::Builder*
+    OS2Table::Builder::CreateBuilder(Header* header,
+                                     WritableFontData* data) {
+  Ptr<OS2Table::Builder> builder;
+  builder = new OS2Table::Builder(header, data);
+  return builder.Detach();
+}
+
+int32_t OS2Table::Builder::TableVersion() {
+  return InternalReadData()->ReadUShort(Offset::kVersion);
+}
+
+void OS2Table::Builder::SetTableVersion(int32_t version) {
+  InternalWriteData()->WriteUShort(Offset::kVersion, version);
+}
+
+int32_t OS2Table::Builder::XAvgCharWidth() {
+  return InternalReadData()->ReadShort(Offset::kXAvgCharWidth);
+}
+
+void OS2Table::Builder::SetXAvgCharWidth(int32_t width) {
+  InternalWriteData()->WriteShort(Offset::kXAvgCharWidth, width);
+}
+
+int32_t OS2Table::Builder::UsWeightClass() {
+  return InternalReadData()->ReadUShort(Offset::kUsWeightClass);
+}
+
+void OS2Table::Builder::SetUsWeightClass(int32_t weight) {
+  InternalWriteData()->WriteUShort(Offset::kUsWeightClass, weight);
+}
+
+int32_t OS2Table::Builder::UsWidthClass() {
+  return InternalReadData()->ReadUShort(Offset::kUsWidthClass);
+}
+
+void OS2Table::Builder::SetUsWidthClass(int32_t width) {
+  InternalWriteData()->WriteUShort(Offset::kUsWidthClass, width);
+}
+
+int32_t OS2Table::Builder::FsType() {
+  return InternalReadData()->ReadUShort(Offset::kFsType);
+}
+
+void OS2Table::Builder::SetFsType(int32_t fs_type) {
+  InternalWriteData()->WriteUShort(Offset::kFsType, fs_type);
+}
+
+int32_t OS2Table::Builder::YSubscriptXSize() {
+  return InternalReadData()->ReadShort(Offset::kYSubscriptXSize);
+}
+
+void OS2Table::Builder::SetYSubscriptXSize(int32_t size) {
+  InternalWriteData()->WriteShort(Offset::kYSubscriptXSize, size);
+}
+
+int32_t OS2Table::Builder::YSubscriptYSize() {
+  return InternalReadData()->ReadShort(Offset::kYSubscriptYSize);
+}
+
+void OS2Table::Builder::SetYSubscriptYSize(int32_t size) {
+  InternalWriteData()->WriteShort(Offset::kYSubscriptYSize, size);
+}
+
+int32_t OS2Table::Builder::YSubscriptXOffset() {
+  return InternalReadData()->ReadShort(Offset::kYSubscriptXOffset);
+}
+
+void OS2Table::Builder::SetYSubscriptXOffset(int32_t offset) {
+  InternalWriteData()->WriteShort(Offset::kYSubscriptXOffset, offset);
+}
+
+int32_t OS2Table::Builder::YSubscriptYOffset() {
+  return InternalReadData()->ReadShort(Offset::kYSubscriptYOffset);
+}
+
+void OS2Table::Builder::SetYSubscriptYOffset(int32_t offset) {
+  InternalWriteData()->WriteShort(Offset::kYSubscriptYOffset, offset);
+}
+
+int32_t OS2Table::Builder::YSuperscriptXSize() {
+  return InternalReadData()->ReadShort(Offset::kYSuperscriptXSize);
+}
+
+void OS2Table::Builder::SetYSuperscriptXSize(int32_t size) {
+  InternalWriteData()->WriteShort(Offset::kYSuperscriptXSize, size);
+}
+
+int32_t OS2Table::Builder::YSuperscriptYSize() {
+  return InternalReadData()->ReadShort(Offset::kYSuperscriptYSize);
+}
+
+void OS2Table::Builder::SetYSuperscriptYSize(int32_t size) {
+  InternalWriteData()->WriteShort(Offset::kYSuperscriptYSize, size);
+}
+
+int32_t OS2Table::Builder::YSuperscriptXOffset() {
+  return InternalReadData()->ReadShort(Offset::kYSuperscriptXOffset);
+}
+
+void OS2Table::Builder::SetYSuperscriptXOffset(int32_t offset) {
+  InternalWriteData()->WriteShort(Offset::kYSuperscriptXOffset, offset);
+}
+
+int32_t OS2Table::Builder::YSuperscriptYOffset() {
+  return InternalReadData()->ReadShort(Offset::kYSuperscriptYOffset);
+}
+
+void OS2Table::Builder::SetYSuperscriptYOffset(int32_t offset) {
+  InternalWriteData()->WriteShort(Offset::kYSuperscriptYOffset, offset);
+}
+
+int32_t OS2Table::Builder::YStrikeoutSize() {
+  return InternalReadData()->ReadShort(Offset::kYStrikeoutSize);
+}
+
+void OS2Table::Builder::SetYStrikeoutSize(int32_t size) {
+  InternalWriteData()->WriteShort(Offset::kYStrikeoutSize, size);
+}
+
+int32_t OS2Table::Builder::YStrikeoutPosition() {
+  return InternalReadData()->ReadShort(Offset::kYStrikeoutPosition);
+}
+
+void OS2Table::Builder::SetYStrikeoutPosition(int32_t position) {
+  InternalWriteData()->WriteShort(Offset::kYStrikeoutPosition, position);
+}
+
+int32_t OS2Table::Builder::SFamilyClass() {
+  return InternalReadData()->ReadShort(Offset::kSFamilyClass);
+}
+
+void OS2Table::Builder::SetSFamilyClass(int32_t family) {
+  InternalWriteData()->WriteShort(Offset::kSFamilyClass, family);
+}
+
+void OS2Table::Builder::Panose(ByteVector* value) {
+  assert(value);
+  value->clear();
+  value->resize(Offset::kPanoseLength);
+  InternalReadData()->ReadBytes(Offset::kPanose,
+                                &((*value)[0]),
+                                0,
+                                Offset::kPanoseLength);
+}
+
+void OS2Table::Builder::SetPanose(ByteVector* panose) {
+  assert(panose);
+  if (panose->size() != Offset::kPanoseLength) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IllegalArgumentException("Panose bytes must be exactly 10 in length");
+#endif
+    return;
+  }
+  InternalWriteData()->WriteBytes(Offset::kPanose, panose);
+}
+
+int64_t OS2Table::Builder::UlUnicodeRange1() {
+  return InternalReadData()->ReadULong(Offset::kUlUnicodeRange1);
+}
+
+void OS2Table::Builder::SetUlUnicodeRange1(int64_t range) {
+  InternalWriteData()->WriteULong(Offset::kUlUnicodeRange1, range);
+}
+
+int64_t OS2Table::Builder::UlUnicodeRange2() {
+  return InternalReadData()->ReadULong(Offset::kUlUnicodeRange2);
+}
+
+void OS2Table::Builder::SetUlUnicodeRange2(int64_t range) {
+  InternalWriteData()->WriteULong(Offset::kUlUnicodeRange2, range);
+}
+
+int64_t OS2Table::Builder::UlUnicodeRange3() {
+  return InternalReadData()->ReadULong(Offset::kUlUnicodeRange3);
+}
+
+void OS2Table::Builder::SetUlUnicodeRange3(int64_t range) {
+  InternalWriteData()->WriteULong(Offset::kUlUnicodeRange3, range);
+}
+
+int64_t OS2Table::Builder::UlUnicodeRange4() {
+  return InternalReadData()->ReadULong(Offset::kUlUnicodeRange4);
+}
+
+void OS2Table::Builder::SetUlUnicodeRange4(int64_t range) {
+  InternalWriteData()->WriteULong(Offset::kUlUnicodeRange4, range);
+}
+
+void OS2Table::Builder::AchVendId(ByteVector* b) {
+  assert(b);
+  b->clear();
+  b->resize(4);
+  InternalReadData()->ReadBytes(Offset::kAchVendId, &((*b)[0]), 0, 4);
+}
+
+void OS2Table::Builder::SetAchVendId(ByteVector* b) {
+  assert(b);
+  assert(b->size());
+  InternalWriteData()->WriteBytesPad(Offset::kAchVendId,
+                                     b,
+                                     0,
+                                     std::min<size_t>(
+                                         (size_t)Offset::kAchVendIdLength,
+                                         b->size()),
+                                     static_cast<byte_t>(' '));
+}
+
+int32_t OS2Table::Builder::FsSelection() {
+  return InternalReadData()->ReadUShort(Offset::kFsSelection);
+}
+
+void OS2Table::Builder::SetFsSelection(int32_t fs_selection) {
+  InternalWriteData()->WriteUShort(Offset::kFsSelection, fs_selection);
+}
+
+int32_t OS2Table::Builder::UsFirstCharIndex() {
+  return InternalReadData()->ReadUShort(Offset::kUsFirstCharIndex);
+}
+
+void OS2Table::Builder::SetUsFirstCharIndex(int32_t first_index) {
+  InternalWriteData()->WriteUShort(Offset::kUsFirstCharIndex, first_index);
+}
+
+int32_t OS2Table::Builder::UsLastCharIndex() {
+  return InternalReadData()->ReadUShort(Offset::kUsLastCharIndex);
+}
+
+void OS2Table::Builder::SetUsLastCharIndex(int32_t last_index) {
+  InternalWriteData()->WriteUShort(Offset::kUsLastCharIndex, last_index);
+}
+
+int32_t OS2Table::Builder::STypoAscender() {
+  return InternalReadData()->ReadShort(Offset::kSTypoAscender);
+}
+
+void OS2Table::Builder::SetSTypoAscender(int32_t ascender) {
+  InternalWriteData()->WriteShort(Offset::kSTypoAscender, ascender);
+}
+
+int32_t OS2Table::Builder::STypoDescender() {
+  return InternalReadData()->ReadShort(Offset::kSTypoDescender);
+}
+
+void OS2Table::Builder::SetSTypoDescender(int32_t descender) {
+  InternalWriteData()->WriteShort(Offset::kSTypoDescender, descender);
+}
+
+int32_t OS2Table::Builder::STypoLineGap() {
+  return InternalReadData()->ReadShort(Offset::kSTypoLineGap);
+}
+
+void OS2Table::Builder::SetSTypoLineGap(int32_t line_gap) {
+  InternalWriteData()->WriteShort(Offset::kSTypoLineGap, line_gap);
+}
+
+int32_t OS2Table::Builder::UsWinAscent() {
+  return InternalReadData()->ReadUShort(Offset::kUsWinAscent);
+}
+
+void OS2Table::Builder::SetUsWinAscent(int32_t ascent) {
+  InternalWriteData()->WriteUShort(Offset::kUsWinAscent, ascent);
+}
+
+int32_t OS2Table::Builder::UsWinDescent() {
+  return InternalReadData()->ReadUShort(Offset::kUsWinDescent);
+}
+
+void OS2Table::Builder::SetUsWinDescent(int32_t descent) {
+  InternalWriteData()->WriteUShort(Offset::kUsWinDescent, descent);
+}
+
+int64_t OS2Table::Builder::UlCodePageRange1() {
+  return InternalReadData()->ReadULong(Offset::kUlCodePageRange1);
+}
+
+void OS2Table::Builder::SetUlCodePageRange1(int64_t range) {
+  InternalWriteData()->WriteULong(Offset::kUlCodePageRange1, range);
+}
+
+int64_t OS2Table::Builder::UlCodePageRange2() {
+  return InternalReadData()->ReadULong(Offset::kUlCodePageRange2);
+}
+
+void OS2Table::Builder::SetUlCodePageRange2(int64_t range) {
+  InternalWriteData()->WriteULong(Offset::kUlCodePageRange2, range);
+}
+
+int32_t OS2Table::Builder::SxHeight() {
+  return InternalReadData()->ReadShort(Offset::kSxHeight);
+}
+
+void OS2Table::Builder::SetSxHeight(int32_t height) {
+  InternalWriteData()->WriteShort(Offset::kSxHeight, height);
+}
+
+int32_t OS2Table::Builder::SCapHeight() {
+  return InternalReadData()->ReadShort(Offset::kSCapHeight);
+}
+
+void OS2Table::Builder::SetSCapHeight(int32_t height) {
+  InternalWriteData()->WriteShort(Offset::kSCapHeight, height);
+}
+
+int32_t OS2Table::Builder::UsDefaultChar() {
+  return InternalReadData()->ReadUShort(Offset::kUsDefaultChar);
+}
+
+void OS2Table::Builder::SetUsDefaultChar(int32_t default_char) {
+  InternalWriteData()->WriteUShort(Offset::kUsDefaultChar, default_char);
+}
+
+int32_t OS2Table::Builder::UsBreakChar() {
+  return InternalReadData()->ReadUShort(Offset::kUsBreakChar);
+}
+
+void OS2Table::Builder::SetUsBreakChar(int32_t break_char) {
+  InternalWriteData()->WriteUShort(Offset::kUsBreakChar, break_char);
+}
+
+int32_t OS2Table::Builder::UsMaxContext() {
+  return InternalReadData()->ReadUShort(Offset::kUsMaxContext);
+}
+
+void OS2Table::Builder::SetUsMaxContext(int32_t max_context) {
+  InternalWriteData()->WriteUShort(Offset::kUsMaxContext, max_context);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/core/os2_table.h b/sfntly/cpp/src/sfntly/table/core/os2_table.h
new file mode 100644
index 0000000..00d26d2
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/core/os2_table.h
@@ -0,0 +1,508 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_OS2_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_OS2_TABLE_H_
+
+#include "sfntly/port/refcount.h"
+#include "sfntly/table/table.h"
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+struct WeightClass {
+  enum {
+    kThin = 100,
+    kExtraLight = 200,
+    kUltraLight = 200,
+    kLight = 300,
+    kNormal = 400,
+    kRegular = 400,
+    kMedium = 500,
+    kSemiBold = 600,
+    kDemiBold = 600,
+    kBold = 700,
+    kExtraBold = 800,
+    kUltraBold = 800,
+    kBlack = 900,
+    kHeavy = 900
+  };
+};
+
+struct WidthClass {
+  enum {
+    kUltraCondensed = 1,
+    kExtraCondensed = 2,
+    kCondensed = 3,
+    kSemiCondensed = 4,
+    kMedium = 5,
+    kNormal = 5,
+    kSemiExpanded = 6,
+    kExpanded = 7,
+    kExtraExpanded = 8,
+    kUltraExpanded = 9
+  };
+};
+
+// Flags to indicate the embedding licensing rights for a font.
+struct EmbeddingFlags {
+  enum {
+    kReserved0 = 1 << 0,
+    kRestrictedLicenseEmbedding = 1 << 1,
+    kPreviewAndPrintEmbedding = 1 << 2,
+    kEditableEmbedding = 1 << 3,
+    kReserved4 = 1 << 4,
+    kReserved5 = 1 << 5,
+    kReserved6 = 1 << 6,
+    kReserved7 = 1 << 7,
+    kNoSubsetting = 1 << 8,
+    kBitmapEmbeddingOnly = 1 << 9,
+    kReserved10 = 1 << 10,
+    kReserved11 = 1 << 11,
+    kReserved12 = 1 << 12,
+    kReserved13 = 1 << 13,
+    kReserved14 = 1 << 14,
+    kReserved15 = 1 << 15
+  };
+};
+
+struct UnicodeRange {
+  enum {
+    // Do NOT reorder. This enum relies on the ordering of the data matching the
+    // ordinal numbers of the properties.
+    kBasicLatin,
+    kLatin1Supplement,
+    kLatinExtendedA,
+    kLatinExtendedB,
+    kIPAExtensions,
+    kSpacingModifierLetters,
+    kCombiningDiacriticalMarks,
+    kGreekAndCoptic,
+    kCoptic,
+    kCyrillic,
+    kArmenian,
+    kHebrew,
+    kVai,
+    kArabic,
+    kNKo,
+    kDevanagari,
+    kBengali,
+    kGurmukhi,
+    kGujarati,
+    kOriya,
+    kTamil,
+    kTelugu,
+    kKannada,
+    kMalayalam,
+    kThai,
+    kLao,
+    kGeorgian,
+    kBalinese,
+    kHangulJamo,
+    kLatinExtendedAdditional,
+    kGreekExtended,
+    kGeneralPunctuation,
+    kSuperscriptsAndSubscripts,
+    kCurrencySymbols,
+    kNumberForms,
+    kArrows,
+    kMathematicalOperators,
+    kMiscTechnical,
+    kControlPictures,
+    kOCR,
+    kEnclosedAlphanumerics,
+    kBoxDrawing,
+    kBlockElements,
+    kGeometricShapes,
+    kMiscSymbols,
+    kDingbats,
+    kCJKSymbolsAndPunctuation,
+    kHiragana,
+    kKatakana,
+    kBopomofo,
+    kHangulCompatibilityJamo,
+    kPhagspa,
+    kEnclosedCJKLettersAndMonths,
+    kCJKCompatibility,
+    kHangulSyllables,
+    kNonPlane0,
+    kPhoenician,
+    kCJKUnifiedIdeographs,
+    kPrivateUseAreaPlane0,
+    kCJKStrokes,
+    kAlphabeticPresentationForms,
+    kArabicPresentationFormsA,
+    kCombiningHalfMarks,
+    kVerticalForms,
+    kSmallFormVariants,
+    kArabicPresentationFormsB,
+    kHalfwidthAndFullwidthForms,
+    kSpecials,
+    kTibetan,
+    kSyriac,
+    kThaana,
+    kSinhala,
+    kMyanmar,
+    kEthiopic,
+    kCherokee,
+    kUnifiedCanadianAboriginalSyllabics,
+    kOgham,
+    kRunic,
+    kKhmer,
+    kMongolian,
+    kBraillePatterns,
+    kYiSyllables,
+    kTagalog,
+    kOldItalic,
+    kGothic,
+    kDeseret,
+    kMusicalSymbols,
+    kMathematicalAlphanumericSymbols,
+    kPrivateUsePlane15And16,
+    kVariationSelectors,
+    kTags,
+    kLimbu,
+    kTaiLe,
+    kNewTaiLue,
+    kBuginese,
+    kGlagolitic,
+    kTifnagh,
+    kYijingHexagramSymbols,
+    kSylotiNagari,
+    kLinearB,
+    kAncientGreekNumbers,
+    kUgaritic,
+    kOldPersian,
+    kShavian,
+    kOsmanya,
+    kCypriotSyllabary,
+    kKharoshthi,
+    kTaiXuanJingSymbols,
+    kCuneiform,
+    kCountingRodNumerals,
+    kSudanese,
+    kLepcha,
+    kOlChiki,
+    kSaurashtra,
+    kKayahLi,
+    kRejang,
+    kCharm,
+    kAncientSymbols,
+    kPhaistosDisc,
+    kCarian,
+    kDominoTiles,
+    kReserved123,
+    kReserved124,
+    kReserved125,
+    kReserved126,
+    kReserved127,
+    kLast = kReserved127
+  };
+
+  int32_t range(int32_t bit);
+  // UNIMPLEMENTED: EnumSet<UnicodeRange> asSet(long range1, long range2,
+  //                                            long range3, long range4)
+  //                long[] asArray(EnumSet<UnicodeRange> rangeSet)
+};
+
+struct FsSelection {
+  enum {
+    kITALIC = 1 << 0,
+    kUNDERSCORE = 1 << 1,
+    kNEGATIVE = 1 << 2,
+    kOUTLINED = 1 << 3,
+    kSTRIKEOUT = 1 << 4,
+    kBOLD = 1 << 5,
+    kREGULAR = 1 << 6,
+    kUSE_TYPO_METRICS = 1 << 7,
+    kWWS = 1 << 8,
+    kOBLIQUE = 1 << 9
+  };
+  // UNIMPLEMENTED: EnumSet<FsSelection> asSet(long range1, long range2,
+  //                                           long range3, long range4)
+  //                long[] asArray(EnumSet<FsSelection> rangeSet)
+};
+
+// C++ port only: C++ does not support 64-bit enums until C++0x.  For better
+// portability, we need to use static const int64_t instead.
+struct CodePageRange {
+  static const int64_t kLatin1_1252;
+  static const int64_t kLatin2_1250;
+  static const int64_t kCyrillic_1251;
+  static const int64_t kGreek_1253;
+  static const int64_t kTurkish_1254;
+  static const int64_t kHebrew_1255;
+  static const int64_t kArabic_1256;
+  static const int64_t kWindowsBaltic_1257;
+  static const int64_t kVietnamese_1258;
+  static const int64_t kAlternateANSI9;
+  static const int64_t kAlternateANSI10;
+  static const int64_t kAlternateANSI11;
+  static const int64_t kAlternateANSI12;
+  static const int64_t kAlternateANSI13;
+  static const int64_t kAlternateANSI14;
+  static const int64_t kAlternateANSI15;
+  static const int64_t kThai_874;
+  static const int64_t kJapanJIS_932;
+  static const int64_t kChineseSimplified_936;
+  static const int64_t kKoreanWansung_949;
+  static const int64_t kChineseTraditional_950;
+  static const int64_t kKoreanJohab_1361;
+  static const int64_t kAlternateANSI22;
+  static const int64_t kAlternateANSI23;
+  static const int64_t kAlternateANSI24;
+  static const int64_t kAlternateANSI25;
+  static const int64_t kAlternateANSI26;
+  static const int64_t kAlternateANSI27;
+  static const int64_t kAlternateANSI28;
+  static const int64_t kMacintoshCharacterSet;
+  static const int64_t kOEMCharacterSet;
+  static const int64_t kSymbolCharacterSet;
+  static const int64_t kReservedForOEM32;
+  static const int64_t kReservedForOEM33;
+  static const int64_t kReservedForOEM34;
+  static const int64_t kReservedForOEM35;
+  static const int64_t kReservedForOEM36;
+  static const int64_t kReservedForOEM37;
+  static const int64_t kReservedForOEM38;
+  static const int64_t kReservedForOEM39;
+  static const int64_t kReservedForOEM40;
+  static const int64_t kReservedForOEM41;
+  static const int64_t kReservedForOEM42;
+  static const int64_t kReservedForOEM43;
+  static const int64_t kReservedForOEM44;
+  static const int64_t kReservedForOEM45;
+  static const int64_t kReservedForOEM46;
+  static const int64_t kReservedForOEM47;
+  static const int64_t kIBMGreek_869;
+  static const int64_t kMSDOSRussion_866;
+  static const int64_t kMSDOSNordic_865;
+  static const int64_t kArabic_864;
+  static const int64_t kMSDOSCanadianFrench_863;
+  static const int64_t kHebrew_862;
+  static const int64_t kMSDOSIcelandic_861;
+  static const int64_t kMSDOSPortugese_860;
+  static const int64_t kIBMTurkish_857;
+  static const int64_t kIBMCyrillic_855;
+  static const int64_t kLatin2_852;
+  static const int64_t kMSDOSBaltic_775;
+  static const int64_t kGreek_737;
+  static const int64_t kArabic_708;
+  static const int64_t kLatin1_850;
+  static const int64_t kUS_437;
+
+  // UNIMPLEMENTED: EnumSet<CodePageRange> asSet(long range1, long range2,
+  //                                             long range3, long range4)
+  //                long[] asArray(EnumSet<CodePageRange> rangeSet)
+};
+
+// An OS/2 table - 'OS/2'.
+class OS2Table : public Table, public RefCounted<OS2Table> {
+ public:
+  // A builder for the OS/2 table = 'OS/2'.
+  class Builder : public TableBasedTableBuilder, public RefCounted<Builder> {
+   public:
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    int32_t TableVersion();
+    void SetTableVersion(int32_t version);
+    int32_t XAvgCharWidth();
+    void SetXAvgCharWidth(int32_t width);
+    int32_t UsWeightClass();
+    void SetUsWeightClass(int32_t weight);
+    int32_t UsWidthClass();
+    void SetUsWidthClass(int32_t width);
+    // UNIMPLEMENTED: EnumSet<EmbeddingFlags> fsType()
+    //                void setFsType(EnumSeT<EmbeddingFlags> flagSet)
+    int32_t FsType();
+    void SetFsType(int32_t fs_type);
+    int32_t YSubscriptXSize();
+    void SetYSubscriptXSize(int32_t size);
+    int32_t YSubscriptYSize();
+    void SetYSubscriptYSize(int32_t size);
+    int32_t YSubscriptXOffset();
+    void SetYSubscriptXOffset(int32_t offset);
+    int32_t YSubscriptYOffset();
+    void SetYSubscriptYOffset(int32_t offset);
+    int32_t YSuperscriptXSize();
+    void SetYSuperscriptXSize(int32_t size);
+    int32_t YSuperscriptYSize();
+    void SetYSuperscriptYSize(int32_t size);
+    int32_t YSuperscriptXOffset();
+    void SetYSuperscriptXOffset(int32_t offset);
+    int32_t YSuperscriptYOffset();
+    void SetYSuperscriptYOffset(int32_t offset);
+    int32_t YStrikeoutSize();
+    void SetYStrikeoutSize(int32_t size);
+    int32_t YStrikeoutPosition();
+    void SetYStrikeoutPosition(int32_t position);
+    int32_t SFamilyClass();
+    void SetSFamilyClass(int32_t family);
+    void Panose(ByteVector* value);
+    void SetPanose(ByteVector* panose);
+    int64_t UlUnicodeRange1();
+    void SetUlUnicodeRange1(int64_t range);
+    int64_t UlUnicodeRange2();
+    void SetUlUnicodeRange2(int64_t range);
+    int64_t UlUnicodeRange3();
+    void SetUlUnicodeRange3(int64_t range);
+    int64_t UlUnicodeRange4();
+    void SetUlUnicodeRange4(int64_t range);
+    // UNIMPLEMENTED: EnumSet<UnicodeRange> UlUnicodeRange()
+    //                setUlUnicodeRange(EnumSet<UnicodeRange> rangeSet)
+    void AchVendId(ByteVector* b);
+    // This field is 4 bytes in length and only the first 4 bytes of the byte
+    // array will be written. If the byte array is less than 4 bytes it will be
+    // padded out with space characters (0x20).
+    // @param b ach Vendor Id
+    void SetAchVendId(ByteVector* b);
+    // UNIMPLEMENTED: public EnumSet<FsSelection> fsSelection()
+    int32_t FsSelection();
+    void SetFsSelection(int32_t fs_selection);
+    int32_t UsFirstCharIndex();
+    void SetUsFirstCharIndex(int32_t first_index);
+    int32_t UsLastCharIndex();
+    void SetUsLastCharIndex(int32_t last_index);
+    int32_t STypoAscender();
+    void SetSTypoAscender(int32_t ascender);
+    int32_t STypoDescender();
+    void SetSTypoDescender(int32_t descender);
+    int32_t STypoLineGap();
+    void SetSTypoLineGap(int32_t line_gap);
+    int32_t UsWinAscent();
+    void SetUsWinAscent(int32_t ascent);
+    int32_t UsWinDescent();
+    void SetUsWinDescent(int32_t descent);
+    int64_t UlCodePageRange1();
+    void SetUlCodePageRange1(int64_t range);
+    int64_t UlCodePageRange2();
+    void SetUlCodePageRange2(int64_t range);
+    // UNIMPLEMENTED: EnumSet<CodePageRange> ulCodePageRange()
+    //                void setUlCodePageRange(EnumSet<CodePageRange> rangeSet)
+    int32_t SxHeight();
+    void SetSxHeight(int32_t height);
+    int32_t SCapHeight();
+    void SetSCapHeight(int32_t height);
+    int32_t UsDefaultChar();
+    void SetUsDefaultChar(int32_t default_char);
+    int32_t UsBreakChar();
+    void SetUsBreakChar(int32_t break_char);
+    int32_t UsMaxContext();
+    void SetUsMaxContext(int32_t max_context);
+  };
+
+  ~OS2Table();
+
+  int32_t TableVersion();
+  int32_t XAvgCharWidth();
+  int32_t UsWeightClass();
+  int32_t UsWidthClass();
+  // UNIMPLEMENTED: public EnumSet<EmbeddingFlags> fsType()
+  int32_t FsType();
+  int32_t YSubscriptXSize();
+  int32_t YSubscriptYSize();
+  int32_t YSubscriptXOffset();
+  int32_t YSubscriptYOffset();
+  int32_t YSuperscriptXSize();
+  int32_t YSuperscriptYSize();
+  int32_t YSuperscriptXOffset();
+  int32_t YSuperscriptYOffset();
+  int32_t YStrikeoutSize();
+  int32_t YStrikeoutPosition();
+  int32_t SFamilyClass();
+  void Panose(ByteVector* value);
+  int64_t UlUnicodeRange1();
+  int64_t UlUnicodeRange2();
+  int64_t UlUnicodeRange3();
+  int64_t UlUnicodeRange4();
+  // UNIMPLEMENTED: public EnumSet<UnicodeRange> UlUnicodeRange()
+  void AchVendId(ByteVector* b);
+  // UNIMPLEMENTED: public EnumSet<FsSelection> fsSelection()
+  int32_t FsSelection();
+  int32_t UsFirstCharIndex();
+  int32_t UsLastCharIndex();
+  int32_t STypoAscender();
+  int32_t STypoDescender();
+  int32_t STypoLineGap();
+  int32_t UsWinAscent();
+  int32_t UsWinDescent();
+  int64_t UlCodePageRange1();
+  int64_t UlCodePageRange2();
+  // UNIMPLEMENTED: public EnumSet<CodePageRange> ulCodePageRange()
+  int32_t SxHeight();
+  int32_t SCapHeight();
+  int32_t UsDefaultChar();
+  int32_t UsBreakChar();
+  int32_t UsMaxContext();
+
+ private:
+  struct Offset {
+    enum {
+      kVersion = 0,
+      kXAvgCharWidth = 2,
+      kUsWeightClass = 4,
+      kUsWidthClass = 6,
+      kFsType = 8,
+      kYSubscriptXSize = 10,
+      kYSubscriptYSize = 12,
+      kYSubscriptXOffset = 14,
+      kYSubscriptYOffset = 16,
+      kYSuperscriptXSize = 18,
+      kYSuperscriptYSize = 20,
+      kYSuperscriptXOffset = 22,
+      kYSuperscriptYOffset = 24,
+      kYStrikeoutSize = 26,
+      kYStrikeoutPosition = 28,
+      kSFamilyClass = 30,
+      kPanose = 32,
+      kPanoseLength = 10,  // Length of panose bytes.
+      kUlUnicodeRange1 = 42,
+      kUlUnicodeRange2 = 46,
+      kUlUnicodeRange3 = 50,
+      kUlUnicodeRange4 = 54,
+      kAchVendId = 58,
+      kAchVendIdLength = 4,  // Length of ach vend id bytes.
+      kFsSelection = 62,
+      kUsFirstCharIndex = 64,
+      kUsLastCharIndex = 66,
+      kSTypoAscender = 68,
+      kSTypoDescender = 70,
+      kSTypoLineGap = 72,
+      kUsWinAscent = 74,
+      kUsWinDescent = 76,
+      kUlCodePageRange1 = 78,
+      kUlCodePageRange2 = 82,
+      kSxHeight = 86,
+      kSCapHeight = 88,
+      kUsDefaultChar = 90,
+      kUsBreakChar = 92,
+      kUsMaxContext = 94
+    };
+  };
+
+  OS2Table(Header* header, ReadableFontData* data);
+};
+typedef Ptr<OS2Table> OS2TablePtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_CORE_OS2_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/font_data_table.cc b/sfntly/cpp/src/sfntly/table/font_data_table.cc
new file mode 100644
index 0000000..0e27f7a
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/font_data_table.cc
@@ -0,0 +1,193 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/font_data_table.h"
+
+#include "sfntly/data/font_output_stream.h"
+
+namespace sfntly {
+
+/******************************************************************************
+ * FontDataTable class
+ ******************************************************************************/
+
+FontDataTable::FontDataTable(ReadableFontData* data) {
+  data_ = data;
+}
+
+FontDataTable::~FontDataTable() {}
+
+ReadableFontData* FontDataTable::ReadFontData() {
+  return data_;
+}
+
+int32_t FontDataTable::DataLength() {
+  return data_->Length();
+}
+
+int32_t FontDataTable::Serialize(OutputStream* os) {
+  return data_->CopyTo(os);
+}
+
+int32_t FontDataTable::Serialize(WritableFontData* data) {
+  return data_->CopyTo(data);
+}
+
+/******************************************************************************
+ * FontDataTable::Builder class
+ ******************************************************************************/
+CALLER_ATTACH WritableFontData* FontDataTable::Builder::Data() {
+  WritableFontDataPtr new_data;
+  if (model_changed_) {
+    if (!SubReadyToSerialize()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IOException("Table not ready to build.");
+#endif
+      return NULL;
+    }
+    int32_t size = SubDataSizeToSerialize();
+    new_data.Attach(WritableFontData::CreateWritableFontData(size));
+    SubSerialize(new_data);
+  } else {
+    ReadableFontDataPtr data = InternalReadData();
+    new_data.Attach(WritableFontData::CreateWritableFontData(
+                        data != NULL ? data->Length() : 0));
+    if (data != NULL) {
+      data->CopyTo(new_data);
+    }
+  }
+  return new_data.Detach();
+}
+
+void FontDataTable::Builder::SetData(ReadableFontData* data) {
+  InternalSetData(data, true);
+}
+
+
+CALLER_ATTACH FontDataTable* FontDataTable::Builder::Build() {
+  FontDataTablePtr table;  // NULL default table
+  ReadableFontDataPtr data = InternalReadData();
+  if (model_changed_) {
+    // Let subclass serialize from model.
+    if (!SubReadyToSerialize()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IOException("Table not ready to build.");
+#endif
+      return NULL;
+    }
+    int32_t size = SubDataSizeToSerialize();
+    WritableFontDataPtr new_data;
+    new_data.Attach(WritableFontData::CreateWritableFontData(size));
+    SubSerialize(new_data);
+    data = new_data;
+  }
+
+  if (data != NULL) {
+    table = SubBuildTable(data);
+    NotifyPostTableBuild(table);
+  }
+
+  r_data_.Release();
+  w_data_.Release();
+  return table;
+}
+
+bool FontDataTable::Builder::ReadyToBuild() {
+  return true;
+}
+
+ReadableFontData* FontDataTable::Builder::InternalReadData() {
+  return (r_data_ != NULL) ? r_data_.p_ :
+                             static_cast<ReadableFontData*>(w_data_.p_);
+}
+
+WritableFontData* FontDataTable::Builder::InternalWriteData() {
+  if (w_data_ == NULL) {
+    WritableFontDataPtr new_data;
+    new_data.Attach(WritableFontData::CreateWritableFontData(
+                        r_data_ == NULL ? 0 : r_data_->Length()));
+#if !defined (SFNTLY_NO_EXCEPTION)
+    try {
+#endif
+      if (r_data_) {
+        r_data_->CopyTo(new_data);
+      }
+#if !defined (SFNTLY_NO_EXCEPTION)
+    } catch (IOException& e) {
+      // TODO(stuartg): fix when IOExceptions are cleaned up
+    }
+#endif
+    InternalSetData(new_data, false);
+  }
+  return w_data_.p_;
+}
+
+FontDataTable::Builder::Builder()
+    : model_changed_(false),
+      contained_model_changed_(false),
+      data_changed_(false) {
+}
+
+FontDataTable::Builder::Builder(int32_t data_size)
+    : model_changed_(false),
+      contained_model_changed_(false),
+      data_changed_(false) {
+  w_data_.Attach(WritableFontData::CreateWritableFontData(data_size));
+}
+
+FontDataTable::Builder::Builder(WritableFontData* data)
+    : model_changed_(false),
+      contained_model_changed_(false),
+      data_changed_(false) {
+  w_data_ = data;
+}
+
+FontDataTable::Builder::Builder(ReadableFontData* data)
+    : model_changed_(false),
+      contained_model_changed_(false),
+      data_changed_(false) {
+  r_data_ = data;
+}
+
+FontDataTable::Builder::~Builder() {
+}
+
+void FontDataTable::Builder::NotifyPostTableBuild(FontDataTable* table) {
+  // Default: NOP.
+  UNREFERENCED_PARAMETER(table);
+}
+
+void FontDataTable::Builder::InternalSetData(WritableFontData* data,
+                                             bool data_changed) {
+  w_data_ = data;
+  r_data_ = NULL;
+  if (data_changed) {
+    data_changed_ = true;
+    SubDataSet();
+  }
+}
+
+void FontDataTable::Builder::InternalSetData(ReadableFontData* data,
+                                             bool data_changed) {
+  w_data_ = NULL;
+  r_data_ = data;
+  if (data_changed) {
+    data_changed_ = true;
+    SubDataSet();
+  }
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/font_data_table.h b/sfntly/cpp/src/sfntly/table/font_data_table.h
new file mode 100644
index 0000000..5e437e2
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/font_data_table.h
@@ -0,0 +1,123 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_FONT_DATA_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_FONT_DATA_TABLE_H_
+
+#include "sfntly/data/readable_font_data.h"
+#include "sfntly/data/writable_font_data.h"
+#include "sfntly/port/refcount.h"
+
+namespace sfntly {
+
+// An abstract base for any table that contains a FontData. This is the root of
+// the table class hierarchy.
+class FontDataTable : virtual public RefCount {
+ public:
+  // Note: original version is abstract Builder<T extends FontDataTable>
+  //       C++ template is not designed that way so plain class is chosen.
+  class Builder : virtual public RefCount {
+   public:
+    // Get a snapshot copy of the internal data of the builder.
+    // This causes any internal data structures to be serialized to a new data
+    // object. This data object belongs to the caller and must be properly
+    // disposed of. No changes are made to the builder and any changes to the
+    // data directly do not affect the internal state. To do that a subsequent
+    // call must be made to {@link #SetData(WritableFontData)}.
+    // @return a copy of the internal data of the builder
+    CALLER_ATTACH WritableFontData* Data();
+    virtual void SetData(ReadableFontData* data);
+
+    // Note: changed from protected to avoid accessibility error in C++
+    virtual CALLER_ATTACH FontDataTable* Build();
+    virtual bool ReadyToBuild();
+
+    ReadableFontData* InternalReadData();
+    WritableFontData* InternalWriteData();
+
+    bool data_changed() { return data_changed_; }
+    bool model_changed() {
+      return current_model_changed() || contained_model_changed();
+    }
+    bool current_model_changed() { return model_changed_; }
+    bool contained_model_changed() { return contained_model_changed_; }
+
+    bool set_model_changed() { return set_model_changed(true); }
+    bool set_model_changed(bool changed) {
+      bool old = model_changed_;
+      model_changed_ = changed;
+      return old;
+    }
+
+   protected:
+    explicit Builder();
+
+    // Construct a FontDataTable.Builder with a WritableFontData backing store
+    // of size given. A positive size will create a fixed size backing store and
+    // a 0 or less size is an estimate for a growable backing store with the
+    // estimate being the absolute of the size.
+    // @param dataSize if positive then a fixed size; if 0 or less then an
+    //        estimate for a growable size
+    Builder(int32_t data_size);
+    Builder(WritableFontData* data);
+    Builder(ReadableFontData* data);
+    virtual ~Builder();
+
+    // subclass API
+    virtual void NotifyPostTableBuild(FontDataTable* table);
+    virtual int32_t SubSerialize(WritableFontData* new_data) = 0;
+    virtual bool SubReadyToSerialize() = 0;
+    virtual int32_t SubDataSizeToSerialize() = 0;
+    virtual void SubDataSet() = 0;
+    virtual CALLER_ATTACH FontDataTable*
+        SubBuildTable(ReadableFontData* data) = 0;
+
+   private:
+    void InternalSetData(WritableFontData* data, bool data_changed);
+    void InternalSetData(ReadableFontData* data, bool data_changed);
+
+    WritableFontDataPtr w_data_;
+    ReadableFontDataPtr r_data_;
+    bool model_changed_;
+    bool contained_model_changed_;  // may expand to list of submodel states
+    bool data_changed_;
+  };
+
+  explicit FontDataTable(ReadableFontData* data);
+  virtual ~FontDataTable();
+
+  // Get the readable font data for this table.
+  ReadableFontData* ReadFontData();
+
+  // Get the length of the data for this table in bytes. This is the full
+  // allocated length of the data underlying the table and may or may not
+  // include any padding.
+  virtual int32_t DataLength();
+
+  virtual int32_t Serialize(OutputStream* os);
+
+ protected:
+  virtual int32_t Serialize(WritableFontData* data);
+
+  // TODO(arthurhsu): style guide violation: protected member, need refactoring
+  ReadableFontDataPtr data_;
+};
+typedef Ptr<FontDataTable> FontDataTablePtr;
+typedef Ptr<FontDataTable::Builder> FontDataTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_FONT_DATA_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/generic_table_builder.cc b/sfntly/cpp/src/sfntly/table/generic_table_builder.cc
new file mode 100644
index 0000000..78e6797
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/generic_table_builder.cc
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/generic_table_builder.h"
+
+namespace sfntly {
+
+GenericTableBuilder::~GenericTableBuilder() {}
+
+CALLER_ATTACH
+FontDataTable* GenericTableBuilder::SubBuildTable(ReadableFontData* data) {
+  // Note: In C++ port, we use GenericTable, the ref-counted version of Table
+  UNREFERENCED_PARAMETER(data);
+  Ptr<GenericTable> table = new GenericTable(header(), InternalReadData());
+  return table.Detach();
+}
+
+// static
+CALLER_ATTACH GenericTableBuilder*
+    GenericTableBuilder::CreateBuilder(Header* header, WritableFontData* data) {
+  Ptr<GenericTableBuilder> builder =
+      new GenericTableBuilder(header, data);
+  return builder.Detach();
+}
+
+GenericTableBuilder::GenericTableBuilder(Header* header,
+                                         WritableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+GenericTableBuilder::GenericTableBuilder(Header* header,
+                                         ReadableFontData* data)
+    : TableBasedTableBuilder(header, data) {
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/generic_table_builder.h b/sfntly/cpp/src/sfntly/table/generic_table_builder.h
new file mode 100644
index 0000000..a100ea0
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/generic_table_builder.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_GENERIC_TABLE_BUILDER_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_GENERIC_TABLE_BUILDER_H_
+
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+// A table builder to do the minimal table building for an unknown table type.
+class GenericTableBuilder : public TableBasedTableBuilder,
+                            public RefCounted<GenericTableBuilder> {
+ public:
+  virtual ~GenericTableBuilder();
+
+  virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+
+  static CALLER_ATTACH GenericTableBuilder*
+      CreateBuilder(Header* header, WritableFontData* data);
+
+ private:
+  GenericTableBuilder(Header* header, WritableFontData* data);
+  GenericTableBuilder(Header* header, ReadableFontData* data);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_BYTE_ARRAY_TABLE_BUILDER_H_
diff --git a/sfntly/cpp/src/sfntly/table/header.cc b/sfntly/cpp/src/sfntly/table/header.cc
new file mode 100644
index 0000000..672ace5
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/header.cc
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/header.h"
+
+namespace sfntly {
+
+/******************************************************************************
+ * Header class
+ ******************************************************************************/
+Header::Header(int32_t tag)
+    : tag_(tag),
+      offset_(0),
+      offset_valid_(false),
+      length_(0),
+      length_valid_(false),
+      checksum_(0),
+      checksum_valid_(false) {
+}
+
+Header::Header(int32_t tag, int32_t length)
+    : tag_(tag),
+      offset_(0),
+      offset_valid_(false),
+      length_(length),
+      length_valid_(true),
+      checksum_(0),
+      checksum_valid_(false) {
+}
+
+Header::Header(int32_t tag, int64_t checksum, int32_t offset, int32_t length)
+    : tag_(tag),
+      offset_(offset),
+      offset_valid_(true),
+      length_(length),
+      length_valid_(true),
+      checksum_(checksum),
+      checksum_valid_(true) {
+}
+
+Header::~Header() {}
+
+bool HeaderComparatorByOffset::operator() (const HeaderPtr lhs,
+                                           const HeaderPtr rhs) {
+  return lhs->offset_ > rhs->offset_;
+}
+
+bool HeaderComparatorByTag::operator() (const HeaderPtr lhs,
+                                        const HeaderPtr rhs) {
+  return lhs->tag_ > rhs->tag_;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/header.h b/sfntly/cpp/src/sfntly/table/header.h
new file mode 100644
index 0000000..280e556
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/header.h
@@ -0,0 +1,114 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_HEADER_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_HEADER_H_
+
+#include "sfntly/port/refcount.h"
+
+namespace sfntly {
+
+class Header : public RefCounted<Header> {
+ public:
+  // Make a partial header with only the basic info for an empty new table.
+  explicit Header(int32_t tag);
+
+  // Make a partial header with only the basic info for a new table.
+  Header(int32_t tag, int32_t length);
+
+  // Make a full header as read from an existing font.
+  Header(int32_t tag, int64_t checksum, int32_t offset, int32_t length);
+  virtual ~Header();
+
+  // Get the table tag.
+  int32_t tag() { return tag_; }
+
+  // Get the table offset. The offset is from the start of the font file.  This
+  // offset value is what was read from the font file during construction of the
+  // font. It may not be meaningful if the font was maninpulated through the
+  // builders.
+  int32_t offset() { return offset_; }
+
+  // Is the offset in the header valid. The offset will not be valid if the
+  // table was constructed during building and has no physical location in a
+  // font file.
+  bool offset_valid() { return offset_valid_; }
+
+  // Get the length of the table as recorded in the table record header.  During
+  // building the header length will reflect the length that was initially read
+  // from the font file. This may not be consistent with the current state of
+  // the data.
+  int32_t length() { return length_; }
+
+  // Is the length in the header valid. The length will not be valid if the
+  // table was constructed during building and has no physical location in a
+  // font file until the table is built from the builder.
+  bool length_valid() { return length_valid_; }
+
+  // Get the checksum for the table as recorded in the table record header.
+  int64_t checksum() { return checksum_; }
+
+  // Is the checksum valid. The checksum will not be valid if the table was
+  // constructed during building and has no physical location in a font file.
+  // Note that this does *NOT* check the validity of the checksum against
+  // the calculated checksum for the table data.
+  bool checksum_valid() { return checksum_valid_; }
+
+  // UNIMPLEMENTED: boolean equals(Object obj)
+  //                int hashCode()
+  //                string toString()
+
+ private:
+  int32_t tag_;
+  int32_t offset_;
+  bool offset_valid_;
+  int32_t length_;
+  bool length_valid_;
+  int64_t checksum_;
+  bool checksum_valid_;
+
+  friend class HeaderComparatorByOffset;
+  friend class HeaderComparatorByTag;
+};
+typedef Ptr<Header> HeaderPtr;
+
+class HeaderComparator {
+ public:
+  virtual ~HeaderComparator() {}
+  virtual bool operator()(const HeaderPtr h1,
+                          const HeaderPtr h2) = 0;
+};
+
+class HeaderComparatorByOffset : public HeaderComparator {
+ public:
+  virtual ~HeaderComparatorByOffset() {}
+  virtual bool operator()(const HeaderPtr h1,
+                          const HeaderPtr h2);
+};
+
+class HeaderComparatorByTag : public HeaderComparator {
+ public:
+  virtual ~HeaderComparatorByTag() {}
+  virtual bool operator()(const HeaderPtr h1,
+                          const HeaderPtr h2);
+};
+
+typedef std::set<HeaderPtr, HeaderComparatorByOffset> HeaderOffsetSortedSet;
+typedef std::set<HeaderPtr, HeaderComparatorByTag> HeaderTagSortedSet;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_HEADER_H_
diff --git a/sfntly/cpp/src/sfntly/table/subtable.cc b/sfntly/cpp/src/sfntly/table/subtable.cc
new file mode 100644
index 0000000..e5b906f
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/subtable.cc
@@ -0,0 +1,64 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/subtable.h"
+
+namespace sfntly {
+/******************************************************************************
+ * SubTable class
+ ******************************************************************************/
+SubTable::~SubTable() {}
+
+SubTable::SubTable(ReadableFontData* data, ReadableFontData* master_data)
+    : FontDataTable(data), padding_(0) {
+  master_data_ = master_data;
+}
+
+SubTable::SubTable(ReadableFontData* data)
+    : FontDataTable(data), padding_(0) {
+}
+
+/******************************************************************************
+ * SubTable::Builder class
+ ******************************************************************************/
+SubTable::Builder::~Builder() {
+}
+
+SubTable::Builder::Builder(int32_t data_size)
+    : FontDataTable::Builder(data_size) {
+}
+
+SubTable::Builder::Builder(WritableFontData* data,
+                           ReadableFontData* master_data)
+    : FontDataTable::Builder(data) {
+  master_data_ = master_data;
+}
+
+SubTable::Builder::Builder(ReadableFontData* data,
+                           ReadableFontData* master_data)
+    : FontDataTable::Builder(data) {
+  master_data_ = master_data;
+}
+
+SubTable::Builder::Builder(WritableFontData* data)
+    : FontDataTable::Builder(data) {
+}
+
+SubTable::Builder::Builder(ReadableFontData* data)
+    : FontDataTable::Builder(data) {
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/subtable.h b/sfntly/cpp/src/sfntly/table/subtable.h
new file mode 100644
index 0000000..fa6f4c6
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/subtable.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_SUBTABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_SUBTABLE_H_
+
+#include "sfntly/table/font_data_table.h"
+
+namespace sfntly {
+
+// An abstract base class for subtables. Subtables are smaller tables nested
+// within other tables and don't have an entry in the main font index. Examples
+// of these are the CMap subtables within CMap table (cmap) or a glyph within
+// the glyph table (glyf).
+class SubTable : public FontDataTable {
+ public:
+  class Builder : public FontDataTable::Builder {
+   public:
+    virtual ~Builder();
+
+   protected:
+    // @param data the data for the subtable being built
+    // @param master_data the data for the full table
+    Builder(int32_t data_size);
+    Builder(WritableFontData* data, ReadableFontData* master_data);
+    Builder(ReadableFontData* data, ReadableFontData* master_data);
+    explicit Builder(WritableFontData* data);
+    explicit Builder(ReadableFontData* data);
+
+    ReadableFontData* master_read_data() { return master_data_; }
+
+   private:
+    ReadableFontDataPtr master_data_;
+  };
+
+  virtual ~SubTable();
+  virtual int32_t Padding() { return padding_; }
+
+  // Sets the amount of padding that is part of the data being used by this
+  // subtable.
+  void set_padding(int32_t padding) { padding_ = padding; }
+
+ protected:
+  SubTable(ReadableFontData* data, ReadableFontData* master_data);
+
+  // Note: constructor refactored in C++ to avoid heavy lifting.
+  //       caller need to do data->Slice(offset, length) beforehand.
+  explicit SubTable(ReadableFontData* data);
+
+  ReadableFontData* master_read_data() { return master_data_; }
+
+ private:
+  // The data for the whole table in which this subtable is contained.
+  ReadableFontDataPtr master_data_;
+  int32_t padding_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_SUBTABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/subtable_container_table.h b/sfntly/cpp/src/sfntly/table/subtable_container_table.h
new file mode 100644
index 0000000..0f099de
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/subtable_container_table.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_SFNTLY_TABLE_SUBTABLE_CONTAINER_TABLE_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_SFNTLY_TABLE_SUBTABLE_CONTAINER_TABLE_H_
+
+#include "sfntly/table/table.h"
+
+namespace sfntly {
+
+class SubTableContainerTable : public Table {
+ public:
+  class Builder : public Table::Builder {
+   public:
+    Builder(Header* header, WritableFontData* data)
+        : Table::Builder(header, data) {
+    }
+
+    Builder(Header* header, ReadableFontData* data)
+        : Table::Builder(header, data) {
+    }
+
+    virtual ~Builder() {}
+  };
+
+  SubTableContainerTable(Header* header, ReadableFontData* data)
+      : Table(header, data) {
+  }
+
+  virtual ~SubTableContainerTable() {}
+};
+
+}  // namespace sfntly
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_SFNTLY_TABLE_SUBTABLE_CONTAINER_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/table.cc b/sfntly/cpp/src/sfntly/table/table.cc
new file mode 100644
index 0000000..cf574b8
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/table.cc
@@ -0,0 +1,162 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// type.h needs to be included first because of building issues on Windows
+// Type aliases we delcare are defined in other headers and make the build
+// fail otherwise.
+#include "sfntly/port/type.h"
+#include "sfntly/table/table.h"
+
+#include "sfntly/font.h"
+#include "sfntly/tag.h"
+#include "sfntly/table/bitmap/ebdt_table.h"
+#include "sfntly/table/bitmap/eblc_table.h"
+#include "sfntly/table/bitmap/ebsc_table.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/table/core/font_header_table.h"
+#include "sfntly/table/core/horizontal_device_metrics_table.h"
+#include "sfntly/table/core/horizontal_header_table.h"
+#include "sfntly/table/core/horizontal_metrics_table.h"
+#include "sfntly/table/core/maximum_profile_table.h"
+#include "sfntly/table/core/name_table.h"
+#include "sfntly/table/core/os2_table.h"
+#include "sfntly/table/generic_table_builder.h"
+#include "sfntly/table/table_based_table_builder.h"
+#include "sfntly/table/truetype/glyph_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+
+namespace sfntly {
+
+/******************************************************************************
+ * Table class
+ ******************************************************************************/
+Table::~Table() {}
+
+int64_t Table::CalculatedChecksum() {
+  return data_->Checksum();
+}
+
+void Table::SetFont(Font* font) {
+  font_ = font;
+}
+
+Table::Table(Header* header, ReadableFontData* data)
+    : FontDataTable(data) {
+  header_ = header;
+}
+
+/******************************************************************************
+ * Table::Builder class
+ ******************************************************************************/
+Table::Builder::~Builder() {
+  header_.Release();
+}
+
+void Table::Builder::NotifyPostTableBuild(FontDataTable* table) {
+  if (model_changed() || data_changed()) {
+    Table* derived_table = down_cast<Table*>(table);
+    derived_table->header_ = new Header(header()->tag(),
+                                        derived_table->DataLength());
+  }
+}
+
+CALLER_ATTACH
+Table::Builder* Table::Builder::GetBuilder(Header* header,
+                                           WritableFontData* table_data) {
+  int32_t tag = header->tag();
+  Table::Builder* builder_raw = NULL;
+
+  // Note: Tables are commented out when they are not used/ported.
+  // TODO(arthurhsu): IMPLEMENT: finish tables that are not ported.
+  if (tag == Tag::head) {
+    builder_raw = static_cast<Table::Builder*>(
+        FontHeaderTable::Builder::CreateBuilder(header, table_data));
+#if defined (SFNTLY_EXPERIMENTAL)
+  } else if (tag == Tag::cmap) {
+    builder_raw = static_cast<Table::Builder*>(
+        CMapTable::Builder::CreateBuilder(header, table_data));
+#endif  // SFNTLY_EXPERIMENTAL
+  } else if (tag == Tag::hhea) {
+    builder_raw = static_cast<Table::Builder*>(
+        HorizontalHeaderTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::hmtx) {
+    builder_raw = static_cast<Table::Builder*>(
+        HorizontalMetricsTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::maxp) {
+    builder_raw = static_cast<Table::Builder*>(
+        MaximumProfileTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::name) {
+    builder_raw = static_cast<Table::Builder*>(
+        NameTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::OS_2) {
+    builder_raw = static_cast<Table::Builder*>(
+        OS2Table::Builder::CreateBuilder(header, table_data));
+  }/* else if (tag == Tag::PostScript) {
+    builder_raw = static_cast<Table::Builder*>(
+        PostScriptTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::cvt) {
+    builder_raw = static_cast<Table::Builder*>(
+        ControlValueTable::Builder::CreateBuilder(header, table_data));
+  }*/ else if (tag == Tag::glyf) {
+    builder_raw = static_cast<Table::Builder*>(
+        GlyphTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::loca) {
+    builder_raw = static_cast<Table::Builder*>(
+        LocaTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::EBDT || tag == Tag::bdat) {
+    builder_raw = static_cast<Table::Builder*>(
+        EbdtTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::EBLC || tag == Tag::bloc) {
+    builder_raw = static_cast<Table::Builder*>(
+        EblcTable::Builder::CreateBuilder(header, table_data));
+  } else if (tag == Tag::EBSC) {
+    builder_raw = static_cast<Table::Builder*>(
+        EbscTable::Builder::CreateBuilder(header, table_data));
+  } /* else if (tag == Tag::prep) {
+    builder_raw = static_cast<Table::Builder*>(
+        ControlProgramTable::Builder::CreateBuilder(header, table_data));
+  }*/ else if (tag == Tag::bhed) {
+    builder_raw = static_cast<Table::Builder*>(
+        FontHeaderTable::Builder::CreateBuilder(header, table_data));
+#if defined (SFNTLY_EXPERIMENTAL)
+  } else if (tag == Tag::hdmx) {
+    builder_raw = static_cast<Table::Builder*>(
+        HorizontalDeviceMetricsTable::Builder::CreateBuilder(header,
+                                                             table_data));
+#endif  // SFNTLY_EXPERIMENTAL
+  } else {
+    builder_raw = static_cast<Table::Builder*>(
+        GenericTableBuilder::CreateBuilder(header, table_data));
+  }
+
+  return builder_raw;
+}
+
+Table::Builder::Builder(Header* header, WritableFontData* data)
+    : FontDataTable::Builder(data) {
+  header_ = header;
+}
+
+Table::Builder::Builder(Header* header, ReadableFontData* data)
+    : FontDataTable::Builder(data) {
+  header_ = header;
+}
+
+Table::Builder::Builder(Header* header) {
+  header_ = header;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/table.h b/sfntly/cpp/src/sfntly/table/table.h
new file mode 100644
index 0000000..6ebc22d
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/table.h
@@ -0,0 +1,119 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_TABLE_H_
+
+#include <set>
+#include <map>
+#include <vector>
+#include <utility>
+
+#include "sfntly/port/type.h"
+#include "sfntly/table/font_data_table.h"
+#include "sfntly/table/header.h"
+
+namespace sfntly {
+class Font;
+
+// A concrete implementation of a root level table in the font. This is the base
+// class used for all specific table implementations and is used as the generic
+// table for all tables which have no specific implementations.
+class Table : public FontDataTable {
+ public:
+  // Note: original version is Builder<T extends Table>
+  //       C++ template is not designed that way so plain old inheritance is
+  //       chosen.
+  class Builder : public FontDataTable::Builder {
+   public:
+    virtual ~Builder();
+    virtual Header* header() { return header_; }
+    virtual void NotifyPostTableBuild(FontDataTable* table);
+
+    // Get a builder for the table type specified by the data in the header.
+    // @param header the header for the table
+    // @param tableData the data to be used to build the table from
+    // @return builder for the table specified
+    static CALLER_ATTACH Builder* GetBuilder(Header* header,
+                                             WritableFontData* table_data);
+
+    // UNIMPLEMENTED: toString()
+
+   protected:
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    Builder(Header* header);
+
+   private:
+    Ptr<Header> header_;
+  };
+
+  // Note: GenericTableBuilder moved to table_based_table_builder.h to avoid
+  //       circular inclusion.
+
+  virtual ~Table();
+
+  // Get the calculated checksum for the data in the table.
+  virtual int64_t CalculatedChecksum();
+
+  // Get the header for the table.
+  virtual Header* header()          { return header_; }
+
+  // Get the tag for the table from the record header.
+  virtual int32_t header_tag()      { return header_->tag(); }
+
+  // Get the offset for the table from the record header.
+  virtual int32_t header_offset()   { return header_->offset(); }
+
+  // Get the length of the table from the record header.
+  virtual int32_t header_length()   { return header_->length(); }
+
+  // Get the checksum for the table from the record header.
+  virtual int64_t header_checksum() { return header_->checksum(); }
+
+  // UNIMPLEMENTED: toString()
+
+  virtual void SetFont(Font* font);
+
+ protected:
+  Table(Header* header, ReadableFontData* data);
+
+ private:
+  Ptr<Header> header_;
+  Ptr<Font> font_;
+};
+
+// C++ port only
+class GenericTable : public Table, public RefCounted<GenericTable> {
+ public:
+  GenericTable(Header* header, ReadableFontData* data) : Table(header, data) {}
+  virtual ~GenericTable() {}
+};
+
+typedef Ptr<Table> TablePtr;
+typedef std::vector<HeaderPtr> TableHeaderList;
+typedef Ptr<Table::Builder> TableBuilderPtr;
+typedef std::map<int32_t, TablePtr> TableMap;
+typedef std::pair<int32_t, TablePtr> TableMapEntry;
+
+typedef std::map<HeaderPtr, WritableFontDataPtr> DataBlockMap;
+typedef std::pair<HeaderPtr, WritableFontDataPtr> DataBlockEntry;
+typedef std::map<int32_t, TableBuilderPtr> TableBuilderMap;
+typedef std::pair<int32_t, TableBuilderPtr> TableBuilderEntry;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/table_based_table_builder.cc b/sfntly/cpp/src/sfntly/table/table_based_table_builder.cc
new file mode 100644
index 0000000..b505704
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/table_based_table_builder.cc
@@ -0,0 +1,69 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/table_based_table_builder.h"
+
+namespace sfntly {
+
+/******************************************************************************
+ * TableBasedTableBuilder class
+ ******************************************************************************/
+TableBasedTableBuilder::~TableBasedTableBuilder() {}
+
+int32_t TableBasedTableBuilder::SubSerialize(WritableFontData* data) {
+  UNREFERENCED_PARAMETER(data);
+  return 0;
+}
+
+bool TableBasedTableBuilder::SubReadyToSerialize() {
+  return false;
+}
+
+int32_t TableBasedTableBuilder::SubDataSizeToSerialize() {
+  return 0;
+}
+
+void TableBasedTableBuilder::SubDataSet() {
+  table_ = NULL;
+}
+
+CALLER_ATTACH FontDataTable* TableBasedTableBuilder::Build() {
+  FontDataTablePtr table = static_cast<FontDataTable*>(GetTable());
+  return table.Detach();
+}
+
+TableBasedTableBuilder::TableBasedTableBuilder(Header* header,
+                                               WritableFontData* data)
+    : Table::Builder(header, data) {
+}
+
+TableBasedTableBuilder::TableBasedTableBuilder(Header* header,
+                                               ReadableFontData* data)
+    : Table::Builder(header, data) {
+}
+
+TableBasedTableBuilder::TableBasedTableBuilder(Header* header)
+    : Table::Builder(header) {
+}
+
+Table* TableBasedTableBuilder::GetTable() {
+  if (table_ == NULL) {
+    table_.Attach(down_cast<Table*>(SubBuildTable(InternalReadData())));
+  }
+  return table_;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/table_based_table_builder.h b/sfntly/cpp/src/sfntly/table/table_based_table_builder.h
new file mode 100644
index 0000000..d88eefd
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/table_based_table_builder.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_TABLE_BASED_TABLE_BUILDER_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_TABLE_BASED_TABLE_BUILDER_H_
+
+#include "sfntly/table/table.h"
+
+namespace sfntly {
+
+class TableBasedTableBuilder : public Table::Builder {
+ public:
+  virtual ~TableBasedTableBuilder();
+
+  virtual int32_t SubSerialize(WritableFontData* new_data);
+  virtual bool SubReadyToSerialize();
+  virtual int32_t SubDataSizeToSerialize();
+  virtual void SubDataSet();
+  virtual CALLER_ATTACH FontDataTable* Build();
+
+ protected:
+  TableBasedTableBuilder(Header* header, WritableFontData* data);
+  TableBasedTableBuilder(Header* header, ReadableFontData* data);
+  explicit TableBasedTableBuilder(Header* header);
+
+  // C++ port: renamed table() to GetTable()
+  virtual Table* GetTable();
+
+  // TODO(arthurhsu): style guide violation: protected member, need refactor
+  TablePtr table_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_TABLE_BASED_TABLE_BUILDER_H_
diff --git a/sfntly/cpp/src/sfntly/table/truetype/glyph_table.cc b/sfntly/cpp/src/sfntly/table/truetype/glyph_table.cc
new file mode 100644
index 0000000..f38fac5
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/truetype/glyph_table.cc
@@ -0,0 +1,679 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/truetype/glyph_table.h"
+
+#include <stdlib.h>
+
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+/******************************************************************************
+ * Constants
+ ******************************************************************************/
+const int32_t GlyphTable::SimpleGlyph::kFLAG_ONCURVE = 1;
+const int32_t GlyphTable::SimpleGlyph::kFLAG_XSHORT = 1 << 1;
+const int32_t GlyphTable::SimpleGlyph::kFLAG_YSHORT = 1 << 2;
+const int32_t GlyphTable::SimpleGlyph::kFLAG_REPEAT = 1 << 3;
+const int32_t GlyphTable::SimpleGlyph::kFLAG_XREPEATSIGN = 1 << 4;
+const int32_t GlyphTable::SimpleGlyph::kFLAG_YREPEATSIGN = 1 << 5;
+
+const int32_t GlyphTable::CompositeGlyph::kFLAG_ARG_1_AND_2_ARE_WORDS = 1 << 0;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_ARGS_ARE_XY_VALUES = 1 << 1;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_ROUND_XY_TO_GRID = 1 << 2;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_WE_HAVE_A_SCALE = 1 << 3;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_RESERVED = 1 << 4;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_MORE_COMPONENTS = 1 << 5;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_WE_HAVE_AN_X_AND_Y_SCALE = 1 << 6;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_WE_HAVE_A_TWO_BY_TWO = 1 << 7;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_WE_HAVE_INSTRUCTIONS = 1 << 8;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_USE_MY_METRICS = 1 << 9;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_OVERLAP_COMPOUND = 1 << 10;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_SCALED_COMPONENT_OFFSET = 1 << 11;
+const int32_t GlyphTable::CompositeGlyph::kFLAG_UNSCALED_COMPONENT_OFFSET = 1 << 12;
+
+/******************************************************************************
+ * GlyphTable class
+ ******************************************************************************/
+GlyphTable::~GlyphTable() {
+}
+
+GlyphTable::Glyph* GlyphTable::GetGlyph(int32_t offset, int32_t length) {
+  return GlyphTable::Glyph::GetGlyph(this, this->data_, offset, length);
+}
+
+GlyphTable::GlyphTable(Header* header, ReadableFontData* data)
+    : SubTableContainerTable(header, data) {
+}
+
+/******************************************************************************
+ * GlyphTable::Builder class
+ ******************************************************************************/
+GlyphTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : SubTableContainerTable::Builder(header, data) {
+}
+
+GlyphTable::Builder::~Builder() {
+}
+
+void GlyphTable::Builder::SetLoca(const IntegerList& loca) {
+  loca_ = loca;
+  set_model_changed(false);
+  glyph_builders_.clear();
+}
+
+void GlyphTable::Builder::GenerateLocaList(IntegerList* locas) {
+  assert(locas);
+  GlyphBuilderList* glyph_builders = GetGlyphBuilders();
+  locas->push_back(0);
+  if (glyph_builders->size() == 0) {
+    locas->push_back(0);
+  } else {
+    int32_t total = 0;
+    for (GlyphBuilderList::iterator b = glyph_builders->begin(),
+                                    b_end = glyph_builders->end();
+                                    b != b_end; ++b) {
+      int32_t size = (*b)->SubDataSizeToSerialize();
+      locas->push_back(total + size);
+      total += size;
+    }
+  }
+}
+
+CALLER_ATTACH GlyphTable::Builder*
+    GlyphTable::Builder::CreateBuilder(Header* header, WritableFontData* data) {
+  Ptr<GlyphTable::Builder> builder;
+  builder = new GlyphTable::Builder(header, data);
+  return builder.Detach();
+}
+
+GlyphTable::GlyphBuilderList* GlyphTable::Builder::GlyphBuilders() {
+  return GetGlyphBuilders();
+}
+
+void GlyphTable::Builder::SetGlyphBuilders(GlyphBuilderList* glyph_builders) {
+  glyph_builders_ = *glyph_builders;
+  set_model_changed();
+}
+
+CALLER_ATTACH GlyphTable::Glyph::Builder*
+    GlyphTable::Builder::GlyphBuilder(ReadableFontData* data) {
+  return Glyph::Builder::GetBuilder(this, data);
+}
+
+CALLER_ATTACH FontDataTable*
+    GlyphTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table = new GlyphTable(header(), data);
+  return table.Detach();
+}
+
+void GlyphTable::Builder::SubDataSet() {
+  glyph_builders_.clear();
+  set_model_changed(false);
+}
+
+int32_t GlyphTable::Builder::SubDataSizeToSerialize() {
+  if (glyph_builders_.empty())
+    return 0;
+
+  bool variable = false;
+  int32_t size = 0;
+
+  // Calculate size of each table.
+  for (GlyphBuilderList::iterator b = glyph_builders_.begin(),
+                                  end = glyph_builders_.end(); b != end; ++b) {
+      int32_t glyph_size = (*b)->SubDataSizeToSerialize();
+      size += abs(glyph_size);
+      variable |= glyph_size <= 0;
+  }
+  return variable ? -size : size;
+}
+
+bool GlyphTable::Builder::SubReadyToSerialize() {
+  return !glyph_builders_.empty();
+}
+
+int32_t GlyphTable::Builder::SubSerialize(WritableFontData* new_data) {
+  int32_t size = 0;
+  for (GlyphBuilderList::iterator b = glyph_builders_.begin(),
+                                  end = glyph_builders_.end(); b != end; ++b) {
+    FontDataPtr data;
+    data.Attach(new_data->Slice(size));
+    size += (*b)->SubSerialize(down_cast<WritableFontData*>(data.p_));
+  }
+  return size;
+}
+
+void GlyphTable::Builder::Initialize(ReadableFontData* data,
+                                     const IntegerList& loca) {
+  if (data != NULL) {
+    if (loca_.empty()) {
+      return;
+    }
+    int32_t loca_value;
+    int32_t last_loca_value = loca[0];
+    for (size_t i = 1; i < loca.size(); ++i) {
+      loca_value = loca[i];
+      GlyphBuilderPtr builder;
+      builder.Attach(
+        Glyph::Builder::GetBuilder(this,
+                                   data,
+                                   last_loca_value /*offset*/,
+                                   loca_value - last_loca_value /*length*/));
+      glyph_builders_.push_back(builder);
+      last_loca_value = loca_value;
+    }
+  }
+}
+
+GlyphTable::GlyphBuilderList* GlyphTable::Builder::GetGlyphBuilders() {
+  if (glyph_builders_.empty()) {
+    if (InternalReadData() && !loca_.empty()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IllegalStateException(
+          "Loca values not set - unable to parse glyph data.");
+#endif
+      return NULL;
+    }
+    Initialize(InternalReadData(), loca_);
+    set_model_changed();
+  }
+  return &glyph_builders_;
+}
+
+void GlyphTable::Builder::Revert() {
+  glyph_builders_.clear();
+  set_model_changed(false);
+}
+
+/******************************************************************************
+ * GlyphTable::Glyph class
+ ******************************************************************************/
+GlyphTable::Glyph::~Glyph() {}
+
+CALLER_ATTACH GlyphTable::Glyph*
+    GlyphTable::Glyph::GetGlyph(GlyphTable* table,
+                                ReadableFontData* data,
+                                int32_t offset,
+                                int32_t length) {
+  UNREFERENCED_PARAMETER(table);
+  int32_t type = GlyphType(data, offset, length);
+  GlyphPtr glyph;
+
+  ReadableFontDataPtr sliced_data;
+  sliced_data.Attach(down_cast<ReadableFontData*>(data->Slice(offset, length)));
+  if (type == GlyphType::kSimple) {
+    glyph = new SimpleGlyph(sliced_data);
+  } else {
+    glyph = new CompositeGlyph(sliced_data);
+  }
+  return glyph.Detach();
+}
+
+int32_t GlyphTable::Glyph::Padding() {
+  Initialize();
+  return SubTable::Padding();
+}
+
+int32_t GlyphTable::Glyph::GlyphType() {
+  return glyph_type_;
+}
+
+int32_t GlyphTable::Glyph::NumberOfContours() {
+  return number_of_contours_;
+}
+
+int32_t GlyphTable::Glyph::XMin() {
+  return data_->ReadShort(Offset::kXMin);
+}
+
+int32_t GlyphTable::Glyph::XMax() {
+  return data_->ReadShort(Offset::kXMax);
+}
+
+int32_t GlyphTable::Glyph::YMin() {
+  return data_->ReadShort(Offset::kYMin);
+}
+
+int32_t GlyphTable::Glyph::YMax() {
+  return data_->ReadShort(Offset::kYMax);
+}
+
+GlyphTable::Glyph::Glyph(ReadableFontData* data, int32_t glyph_type)
+    : SubTable(data),
+      glyph_type_(glyph_type) {
+  if (data_->Length() == 0) {
+    number_of_contours_ = 0;
+  } else {
+    // -1 if composite
+    number_of_contours_ = data_->ReadShort(Offset::kNumberOfContours);
+  }
+}
+
+int32_t GlyphTable::Glyph::GlyphType(ReadableFontData* data,
+                                     int32_t offset,
+                                     int32_t length) {
+  if (length == 0) {
+    return GlyphType::kSimple;
+  }
+  int32_t number_of_contours = data->ReadShort(offset);
+  if (number_of_contours >= 0) {
+    return GlyphType::kSimple;
+  }
+  return GlyphType::kComposite;
+}
+
+/******************************************************************************
+ * GlyphTable::Glyph::Builder class
+ ******************************************************************************/
+GlyphTable::Glyph::Builder::~Builder() {
+}
+
+GlyphTable::Glyph::Builder::Builder(WritableFontData* data)
+    : SubTable::Builder(data) {
+}
+
+GlyphTable::Glyph::Builder::Builder(ReadableFontData* data)
+    : SubTable::Builder(data) {
+}
+
+CALLER_ATTACH GlyphTable::Glyph::Builder*
+    GlyphTable::Glyph::Builder::GetBuilder(
+        GlyphTable::Builder* table_builder,
+        ReadableFontData* data) {
+  return GetBuilder(table_builder, data, 0, data->Length());
+}
+
+CALLER_ATTACH GlyphTable::Glyph::Builder*
+    GlyphTable::Glyph::Builder::GetBuilder(
+        GlyphTable::Builder* table_builder,
+        ReadableFontData* data,
+        int32_t offset,
+        int32_t length) {
+  UNREFERENCED_PARAMETER(table_builder);
+  int32_t type = Glyph::GlyphType(data, offset, length);
+  GlyphBuilderPtr builder;
+  ReadableFontDataPtr sliced_data;
+  sliced_data.Attach(down_cast<ReadableFontData*>(data->Slice(offset, length)));
+  if (type == GlyphType::kSimple) {
+    builder = new SimpleGlyph::SimpleGlyphBuilder(sliced_data);
+  } else {
+    builder = new CompositeGlyph::CompositeGlyphBuilder(sliced_data);
+  }
+  return builder.Detach();
+}
+
+void GlyphTable::Glyph::Builder::SubDataSet() {
+  // NOP
+}
+
+int32_t GlyphTable::Glyph::Builder::SubDataSizeToSerialize() {
+  return InternalReadData()->Length();
+}
+
+bool GlyphTable::Glyph::Builder::SubReadyToSerialize() {
+  return true;
+}
+
+int32_t GlyphTable::Glyph::Builder::SubSerialize(WritableFontData* new_data) {
+  return InternalReadData()->CopyTo(new_data);
+}
+
+/******************************************************************************
+ * GlyphTable::SimpleGlyph
+ ******************************************************************************/
+GlyphTable::SimpleGlyph::SimpleGlyph(ReadableFontData* data)
+    : GlyphTable::Glyph(data, GlyphType::kSimple), initialized_(false) {
+}
+
+GlyphTable::SimpleGlyph::~SimpleGlyph() {
+}
+
+int32_t GlyphTable::SimpleGlyph::InstructionSize() {
+  Initialize();
+  return instruction_size_;
+}
+
+CALLER_ATTACH ReadableFontData* GlyphTable::SimpleGlyph::Instructions() {
+  Initialize();
+  return down_cast<ReadableFontData*>(
+             data_->Slice(instructions_offset_, InstructionSize()));
+}
+
+int32_t GlyphTable::SimpleGlyph::NumberOfPoints(int32_t contour) {
+  Initialize();
+  if (contour >= NumberOfContours()) {
+    return 0;
+  }
+  return contour_index_[contour + 1] - contour_index_[contour];
+}
+
+int32_t GlyphTable::SimpleGlyph::XCoordinate(int32_t contour, int32_t point) {
+  Initialize();
+  return x_coordinates_[contour_index_[contour] + point];
+}
+
+int32_t GlyphTable::SimpleGlyph::YCoordinate(int32_t contour, int32_t point) {
+  Initialize();
+  return y_coordinates_[contour_index_[contour] + point];
+}
+
+bool GlyphTable::SimpleGlyph::OnCurve(int32_t contour, int32_t point) {
+  Initialize();
+  return on_curve_[contour_index_[contour] + point];
+}
+
+void GlyphTable::SimpleGlyph::Initialize() {
+  AutoLock lock(initialization_lock_);
+  if (initialized_) {
+    return;
+  }
+
+  if (ReadFontData()->Length() == 0) {
+    instruction_size_ = 0;
+    number_of_points_ = 0;
+    instructions_offset_ = 0;
+    flags_offset_ = 0;
+    x_coordinates_offset_ = 0;
+    y_coordinates_offset_ = 0;
+    return;
+  }
+
+  instruction_size_ = data_->ReadUShort(Offset::kSimpleEndPtsOfCountours +
+      NumberOfContours() * DataSize::kUSHORT);
+  instructions_offset_ = Offset::kSimpleEndPtsOfCountours +
+      (NumberOfContours() + 1) * DataSize::kUSHORT;
+  flags_offset_ = instructions_offset_ + instruction_size_ * DataSize::kBYTE;
+  number_of_points_ = ContourEndPoint(NumberOfContours() - 1) + 1;
+  x_coordinates_.resize(number_of_points_);
+  y_coordinates_.resize(number_of_points_);
+  on_curve_.resize(number_of_points_);
+  ParseData(false);
+  x_coordinates_offset_ = flags_offset_ + flag_byte_count_ * DataSize::kBYTE;
+  y_coordinates_offset_ = x_coordinates_offset_ + x_byte_count_ *
+      DataSize::kBYTE;
+  contour_index_.resize(NumberOfContours() + 1);
+  contour_index_[0] = 0;
+  for (uint32_t contour = 0; contour < contour_index_.size() - 1; ++contour) {
+    contour_index_[contour + 1] = ContourEndPoint(contour) + 1;
+  }
+  ParseData(true);
+  int32_t non_padded_data_length =
+    5 * DataSize::kSHORT +
+    (NumberOfContours() * DataSize::kUSHORT) +
+    DataSize::kUSHORT +
+    (instruction_size_ * DataSize::kBYTE) +
+    (flag_byte_count_ * DataSize::kBYTE) +
+    (x_byte_count_ * DataSize::kBYTE) +
+    (y_byte_count_ * DataSize::kBYTE);
+  set_padding(DataLength() - non_padded_data_length);
+  initialized_ = true;
+}
+
+void GlyphTable::SimpleGlyph::ParseData(bool fill_arrays) {
+  int32_t flag = 0;
+  int32_t flag_repeat = 0;
+  int32_t flag_index = 0;
+  int32_t x_byte_index = 0;
+  int32_t y_byte_index = 0;
+
+  for (int32_t point_index = 0; point_index < number_of_points_;
+       ++point_index) {
+    // get the flag for the current point
+    if (flag_repeat == 0) {
+      flag = FlagAsInt(flag_index++);
+      if ((flag & kFLAG_REPEAT) == kFLAG_REPEAT) {
+        flag_repeat = FlagAsInt(flag_index++);
+      }
+    } else {
+      flag_repeat--;
+    }
+
+    // on the curve?
+    if (fill_arrays) {
+      on_curve_[point_index] = ((flag & kFLAG_ONCURVE) == kFLAG_ONCURVE);
+    }
+    // get the x coordinate
+    if ((flag & kFLAG_XSHORT) == kFLAG_XSHORT) {
+      // single byte x coord value
+      if (fill_arrays) {
+        x_coordinates_[point_index] =
+            data_->ReadUByte(x_coordinates_offset_ + x_byte_index);
+        x_coordinates_[point_index] *=
+            ((flag & kFLAG_XREPEATSIGN) == kFLAG_XREPEATSIGN) ? 1 : -1;
+      }
+      x_byte_index++;
+    } else {
+      // double byte coord value
+      if (!((flag & kFLAG_XREPEATSIGN) == kFLAG_XREPEATSIGN)) {
+        if (fill_arrays) {
+          x_coordinates_[point_index] =
+            data_->ReadShort(x_coordinates_offset_ + x_byte_index);
+        }
+        x_byte_index += 2;
+      }
+    }
+    if (fill_arrays && point_index > 0) {
+      x_coordinates_[point_index] += x_coordinates_[point_index - 1];
+    }
+
+    // get the y coordinate
+    if ((flag & kFLAG_YSHORT) == kFLAG_YSHORT) {
+      if (fill_arrays) {
+        y_coordinates_[point_index] =
+          data_->ReadUByte(y_coordinates_offset_ + y_byte_index);
+        y_coordinates_[point_index] *=
+          ((flag & kFLAG_YREPEATSIGN) == kFLAG_YREPEATSIGN) ? 1 : -1;
+      }
+      y_byte_index++;
+    } else {
+      if (!((flag & kFLAG_YREPEATSIGN) == kFLAG_YREPEATSIGN)) {
+        if (fill_arrays) {
+          y_coordinates_[point_index] =
+            data_->ReadShort(y_coordinates_offset_ + y_byte_index);
+        }
+        y_byte_index += 2;
+      }
+    }
+    if (fill_arrays && point_index > 0) {
+      y_coordinates_[point_index] += y_coordinates_[point_index - 1];
+    }
+  }
+  flag_byte_count_ = flag_index;
+  x_byte_count_ = x_byte_index;
+  y_byte_count_ = y_byte_index;
+}
+
+int32_t GlyphTable::SimpleGlyph::FlagAsInt(int32_t index) {
+  return data_->ReadUByte(flags_offset_ + index * DataSize::kBYTE);
+}
+
+int32_t GlyphTable::SimpleGlyph::ContourEndPoint(int32_t contour) {
+  return data_->ReadUShort(contour * DataSize::kUSHORT +
+                           Offset::kSimpleEndPtsOfCountours);
+}
+
+/******************************************************************************
+ * GlyphTable::SimpleGlyph::Builder
+ ******************************************************************************/
+GlyphTable::SimpleGlyph::SimpleGlyphBuilder::~SimpleGlyphBuilder() {
+}
+
+GlyphTable::SimpleGlyph::SimpleGlyphBuilder::SimpleGlyphBuilder(
+    WritableFontData* data)
+    : Glyph::Builder(data) {
+}
+
+GlyphTable::SimpleGlyph::SimpleGlyphBuilder::SimpleGlyphBuilder(
+    ReadableFontData* data)
+    : Glyph::Builder(data) {
+}
+
+CALLER_ATTACH FontDataTable*
+    GlyphTable::SimpleGlyph::SimpleGlyphBuilder::SubBuildTable(
+        ReadableFontData* data) {
+  FontDataTablePtr table = new SimpleGlyph(data);
+  return table.Detach();
+}
+
+/******************************************************************************
+ * GlyphTable::CompositeGlyph
+ ******************************************************************************/
+GlyphTable::CompositeGlyph::CompositeGlyph(ReadableFontData* data)
+    : GlyphTable::Glyph(data, GlyphType::kComposite),
+      instruction_size_(0),
+      instructions_offset_(0),
+      initialized_(false) {
+  Initialize();
+}
+
+GlyphTable::CompositeGlyph::~CompositeGlyph() {
+}
+
+int32_t GlyphTable::CompositeGlyph::Flags(int32_t contour) {
+  return data_->ReadUShort(contour_index_[contour]);
+}
+
+int32_t GlyphTable::CompositeGlyph::NumGlyphs() {
+  return contour_index_.size();
+}
+
+int32_t GlyphTable::CompositeGlyph::GlyphIndex(int32_t contour) {
+  return data_->ReadUShort(DataSize::kUSHORT + contour_index_[contour]);
+}
+
+int32_t GlyphTable::CompositeGlyph::Argument1(int32_t contour) {
+  int32_t index = 2 * DataSize::kUSHORT + contour_index_[contour];
+  int32_t contour_flags = Flags(contour);
+  if ((contour_flags & kFLAG_ARG_1_AND_2_ARE_WORDS) ==
+                       kFLAG_ARG_1_AND_2_ARE_WORDS) {
+    return data_->ReadUShort(index);
+  }
+  return data_->ReadByte(index);
+}
+
+int32_t GlyphTable::CompositeGlyph::Argument2(int32_t contour) {
+  int32_t index = 2 * DataSize::kUSHORT + contour_index_[contour];
+  int32_t contour_flags = Flags(contour);
+  if ((contour_flags & kFLAG_ARG_1_AND_2_ARE_WORDS) ==
+                       kFLAG_ARG_1_AND_2_ARE_WORDS) {
+    return data_->ReadUShort(index + DataSize::kUSHORT);
+  }
+  return data_->ReadByte(index + DataSize::kUSHORT);
+}
+
+int32_t GlyphTable::CompositeGlyph::TransformationSize(int32_t contour) {
+  int32_t contour_flags = Flags(contour);
+  if ((contour_flags & kFLAG_WE_HAVE_A_SCALE) == kFLAG_WE_HAVE_A_SCALE) {
+      return DataSize::kF2DOT14;
+    } else if ((contour_flags & kFLAG_WE_HAVE_AN_X_AND_Y_SCALE) ==
+                                kFLAG_WE_HAVE_AN_X_AND_Y_SCALE) {
+      return 2 * DataSize::kF2DOT14;
+    } else if ((contour_flags & kFLAG_WE_HAVE_A_TWO_BY_TWO) ==
+                                kFLAG_WE_HAVE_A_TWO_BY_TWO) {
+      return 4 * DataSize::kF2DOT14;
+    }
+    return 0;
+}
+
+void GlyphTable::CompositeGlyph::Transformation(int32_t contour,
+                                                ByteVector* transformation) {
+  int32_t contour_flags = Flags(contour);
+  int32_t index = contour_index_[contour] + 2 * DataSize::kUSHORT;
+  if ((contour_flags & kFLAG_ARG_1_AND_2_ARE_WORDS) ==
+                       kFLAG_ARG_1_AND_2_ARE_WORDS) {
+    index += 2 * DataSize::kSHORT;
+  } else {
+    index += 2 * DataSize::kBYTE;
+  }
+  int32_t tsize = TransformationSize(contour);
+  transformation->resize(tsize);
+  data_->ReadBytes(index, &((*transformation)[0]), 0, tsize);
+}
+
+int32_t GlyphTable::CompositeGlyph::InstructionSize() {
+  return instruction_size_;
+}
+
+CALLER_ATTACH ReadableFontData* GlyphTable::CompositeGlyph::Instructions() {
+  return down_cast<ReadableFontData*>(
+             data_->Slice(instructions_offset_, InstructionSize()));
+}
+
+void GlyphTable::CompositeGlyph::Initialize() {
+  AutoLock lock(initialization_lock_);
+  if (initialized_) {
+    return;
+  }
+
+  int32_t index = 5 * DataSize::kUSHORT;
+  int32_t flags = kFLAG_MORE_COMPONENTS;
+
+  while ((flags & kFLAG_MORE_COMPONENTS) == kFLAG_MORE_COMPONENTS) {
+    contour_index_.push_back(index);
+    flags = data_->ReadUShort(index);
+    index += 2 * DataSize::kUSHORT;  // flags and glyphIndex
+    if ((flags & kFLAG_ARG_1_AND_2_ARE_WORDS) == kFLAG_ARG_1_AND_2_ARE_WORDS) {
+      index += 2 * DataSize::kSHORT;
+    } else {
+      index += 2 * DataSize::kBYTE;
+    }
+    if ((flags & kFLAG_WE_HAVE_A_SCALE) == kFLAG_WE_HAVE_A_SCALE) {
+      index += DataSize::kF2DOT14;
+    } else if ((flags & kFLAG_WE_HAVE_AN_X_AND_Y_SCALE) ==
+                        kFLAG_WE_HAVE_AN_X_AND_Y_SCALE) {
+      index += 2 * DataSize::kF2DOT14;
+    } else if ((flags & kFLAG_WE_HAVE_A_TWO_BY_TWO) ==
+                        kFLAG_WE_HAVE_A_TWO_BY_TWO) {
+      index += 4 * DataSize::kF2DOT14;
+    }
+    int32_t non_padded_data_length = index;
+    if ((flags & kFLAG_WE_HAVE_INSTRUCTIONS) == kFLAG_WE_HAVE_INSTRUCTIONS) {
+      instruction_size_ = data_->ReadUShort(index);
+      index += DataSize::kUSHORT;
+      instructions_offset_ = index;
+      non_padded_data_length = index + (instruction_size_ * DataSize::kBYTE);
+    }
+    set_padding(DataLength() - non_padded_data_length);
+  }
+
+  initialized_ = true;
+}
+
+/******************************************************************************
+ * GlyphTable::CompositeGlyph::Builder
+ ******************************************************************************/
+GlyphTable::CompositeGlyph::CompositeGlyphBuilder::~CompositeGlyphBuilder() {
+}
+
+GlyphTable::CompositeGlyph::CompositeGlyphBuilder::CompositeGlyphBuilder(
+    WritableFontData* data)
+    : Glyph::Builder(data) {
+}
+
+GlyphTable::CompositeGlyph::CompositeGlyphBuilder::CompositeGlyphBuilder(
+    ReadableFontData* data)
+    : Glyph::Builder(data) {
+}
+
+CALLER_ATTACH FontDataTable*
+    GlyphTable::CompositeGlyph::CompositeGlyphBuilder::SubBuildTable(
+        ReadableFontData* data) {
+  FontDataTablePtr table = new CompositeGlyph(data);
+  return table.Detach();
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/truetype/glyph_table.h b/sfntly/cpp/src/sfntly/table/truetype/glyph_table.h
new file mode 100644
index 0000000..4ffddda
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/truetype/glyph_table.h
@@ -0,0 +1,334 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_TRUETYPE_GLYPH_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_TRUETYPE_GLYPH_TABLE_H_
+
+#include <vector>
+
+#include "sfntly/table/table.h"
+#include "sfntly/table/subtable.h"
+#include "sfntly/table/subtable_container_table.h"
+
+namespace sfntly {
+
+struct GlyphType {
+  enum {
+    kSimple = 0,
+    kComposite = 1
+  };
+};
+
+class GlyphTable : public SubTableContainerTable,
+                   public RefCounted<GlyphTable> {
+ public:
+  class Builder;
+  class Glyph : public SubTable {
+   public:
+    // Note: Contour is an empty class for the version ported
+    class Contour {
+     protected:
+      Contour() {}
+      virtual ~Contour() {}
+    };
+
+    class Builder : public SubTable::Builder {
+     public:
+      virtual ~Builder();
+
+     protected:
+      // Incoming table_builder is GlyphTable::Builder*.
+      // Note: constructor refactored in C++ to avoid heavy lifting.
+      //       caller need to do data->Slice(offset, length) beforehand.
+      explicit Builder(WritableFontData* data);
+      explicit Builder(ReadableFontData* data);
+
+      static CALLER_ATTACH Builder*
+          GetBuilder(GlyphTable::Builder* table_builder,
+                     ReadableFontData* data);
+      static CALLER_ATTACH Builder*
+          GetBuilder(GlyphTable::Builder* table_builder,
+                     ReadableFontData* data,
+                     int32_t offset,
+                     int32_t length);
+      virtual void SubDataSet();
+      virtual int32_t SubDataSizeToSerialize();
+      virtual bool SubReadyToSerialize();
+      virtual int32_t SubSerialize(WritableFontData* new_data);
+
+     private:
+      friend class GlyphTable::Builder;
+    };
+
+    virtual ~Glyph();
+    static CALLER_ATTACH Glyph* GetGlyph(GlyphTable* table,
+                                         ReadableFontData* data,
+                                         int32_t offset,
+                                         int32_t length);
+
+    virtual int32_t Padding();
+    virtual int32_t GlyphType();
+    virtual int32_t NumberOfContours();
+    virtual int32_t XMin();
+    virtual int32_t XMax();
+    virtual int32_t YMin();
+    virtual int32_t YMax();
+
+    virtual int32_t InstructionSize() = 0;
+    virtual ReadableFontData* Instructions() = 0;
+
+   protected:
+    // Note: constructor refactored in C++ to avoid heavy lifting.
+    //       caller need to do data->Slice(offset, length) beforehand.
+    Glyph(ReadableFontData* data, int32_t glyph_type);
+    virtual void Initialize() = 0;
+    // Note: Derived class to define initialization_lock_.
+
+   private:
+    static int32_t GlyphType(ReadableFontData* data,
+                             int32_t offset,
+                             int32_t length);
+
+    int32_t glyph_type_;
+    int32_t number_of_contours_;
+  };  // class GlyphTable::Glyph
+  typedef Ptr<GlyphTable::Glyph::Builder> GlyphBuilderPtr;
+  typedef std::vector<GlyphBuilderPtr> GlyphBuilderList;
+
+  class Builder : public SubTableContainerTable::Builder,
+                  public RefCounted<GlyphTable::Builder> {
+   public:
+    // Note: Constructor scope altered to public for base class to instantiate.
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+
+    virtual void SetLoca(const IntegerList& loca);
+    virtual void GenerateLocaList(IntegerList* locas);
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    // Gets the List of glyph builders for the glyph table builder. These may be
+    // manipulated in any way by the caller and the changes will be reflected in
+    // the final glyph table produced.
+    // If there is no current data for the glyph builder or the glyph builders
+    // have not been previously set then this will return an empty glyph builder
+    // List. If there is current data (i.e. data read from an existing font) and
+    // the <code>loca</code> list has not been set or is null, empty, or
+    // invalid, then an empty glyph builder List will be returned.
+    GlyphBuilderList* GlyphBuilders();
+
+    // Replace the internal glyph builders with the one provided. The provided
+    // list and all contained objects belong to this builder.
+    // This call is only required if the entire set of glyphs in the glyph
+    // table builder are being replaced. If the glyph builder list provided from
+    // the GlyphTable.Builder::GlyphBuilders() is being used and modified
+    // then those changes will already be reflected in the glyph table builder.
+    void SetGlyphBuilders(GlyphBuilderList* glyph_builders);
+
+    // Glyph builder factories
+    CALLER_ATTACH Glyph::Builder* GlyphBuilder(ReadableFontData* data);
+
+   protected:  // internal API for building
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+   private:
+    void Initialize(ReadableFontData* data, const IntegerList& loca);
+    GlyphBuilderList* GetGlyphBuilders();
+    void Revert();
+
+    GlyphBuilderList glyph_builders_;
+    IntegerList loca_;
+  };
+
+  class SimpleGlyph : public Glyph, public RefCounted<SimpleGlyph> {
+   public:
+    static const int32_t kFLAG_ONCURVE;
+    static const int32_t kFLAG_XSHORT;
+    static const int32_t kFLAG_YSHORT;
+    static const int32_t kFLAG_REPEAT;
+    static const int32_t kFLAG_XREPEATSIGN;
+    static const int32_t kFLAG_YREPEATSIGN;
+
+    class SimpleContour : public Glyph::Contour {
+     protected:
+      SimpleContour() {}
+      virtual ~SimpleContour() {}
+    };
+
+    class SimpleGlyphBuilder : public Glyph::Builder,
+                               public RefCounted<SimpleGlyphBuilder> {
+     public:
+      virtual ~SimpleGlyphBuilder();
+
+     protected:
+      // Note: constructor refactored in C++ to avoid heavy lifting.
+      //       caller need to do data->Slice(offset, length) beforehand.
+      explicit SimpleGlyphBuilder(WritableFontData* data);
+      explicit SimpleGlyphBuilder(ReadableFontData* data);
+      virtual CALLER_ATTACH FontDataTable*
+          SubBuildTable(ReadableFontData* data);
+
+     private:
+      friend class Glyph::Builder;
+    };
+
+    // Note: constructor refactored in C++ to avoid heavy lifting.
+    //       caller need to do data->Slice(offset, length) beforehand.
+    explicit SimpleGlyph(ReadableFontData* data);
+    virtual ~SimpleGlyph();
+
+    virtual int32_t InstructionSize();
+    virtual CALLER_ATTACH ReadableFontData* Instructions();
+    virtual void Initialize();
+
+    int32_t NumberOfPoints(int32_t contour);
+    int32_t XCoordinate(int32_t contour, int32_t point);
+    int32_t YCoordinate(int32_t contour, int32_t point);
+    bool OnCurve(int32_t contour, int32_t point);
+
+   private:
+    void ParseData(bool fill_arrays);
+    int32_t FlagAsInt(int32_t index);
+    int32_t ContourEndPoint(int32_t contour);
+
+    bool initialized_;
+    Lock initialization_lock_;
+    int32_t instruction_size_;
+    int32_t number_of_points_;
+
+    // start offsets of the arrays
+    int32_t instructions_offset_;
+    int32_t flags_offset_;
+    int32_t x_coordinates_offset_;
+    int32_t y_coordinates_offset_;
+
+    int32_t flag_byte_count_;
+    int32_t x_byte_count_;
+    int32_t y_byte_count_;
+
+    IntegerList x_coordinates_;
+    IntegerList y_coordinates_;
+    std::vector<bool> on_curve_;
+    IntegerList contour_index_;
+  };
+
+  class CompositeGlyph : public Glyph, public RefCounted<CompositeGlyph> {
+   public:
+    static const int32_t kFLAG_ARG_1_AND_2_ARE_WORDS;
+    static const int32_t kFLAG_ARGS_ARE_XY_VALUES;
+    static const int32_t kFLAG_ROUND_XY_TO_GRID;
+    static const int32_t kFLAG_WE_HAVE_A_SCALE;
+    static const int32_t kFLAG_RESERVED;
+    static const int32_t kFLAG_MORE_COMPONENTS;
+    static const int32_t kFLAG_WE_HAVE_AN_X_AND_Y_SCALE;
+    static const int32_t kFLAG_WE_HAVE_A_TWO_BY_TWO;
+    static const int32_t kFLAG_WE_HAVE_INSTRUCTIONS;
+    static const int32_t kFLAG_USE_MY_METRICS;
+    static const int32_t kFLAG_OVERLAP_COMPOUND;
+    static const int32_t kFLAG_SCALED_COMPONENT_OFFSET;
+    static const int32_t kFLAG_UNSCALED_COMPONENT_OFFSET;
+
+    class CompositeGlyphBuilder : public Glyph::Builder,
+                                  public RefCounted<CompositeGlyphBuilder> {
+     public:
+      virtual ~CompositeGlyphBuilder();
+
+     protected:
+      // Note: constructor refactored in C++ to avoid heavy lifting.
+      //       caller need to do data->Slice(offset, length) beforehand.
+      explicit CompositeGlyphBuilder(WritableFontData* data);
+      explicit CompositeGlyphBuilder(ReadableFontData* data);
+
+      virtual CALLER_ATTACH FontDataTable*
+          SubBuildTable(ReadableFontData* data);
+
+     private:
+      friend class Glyph::Builder;
+    };
+
+    // Note: constructor refactored in C++ to avoid heavy lifting.
+    //       caller need to do data->Slice(offset, length) beforehand.
+    explicit CompositeGlyph(ReadableFontData* data);
+    virtual ~CompositeGlyph();
+
+    int32_t Flags(int32_t contour);
+    int32_t NumGlyphs();
+    int32_t GlyphIndex(int32_t contour);
+    int32_t Argument1(int32_t contour);
+    int32_t Argument2(int32_t contour);
+    int32_t TransformationSize(int32_t contour);
+    void Transformation(int32_t contour, ByteVector* transformation);
+    virtual int32_t InstructionSize();
+    virtual CALLER_ATTACH ReadableFontData* Instructions();
+
+   protected:
+    virtual void Initialize();
+
+   private:
+    IntegerList contour_index_;
+    int32_t instruction_size_;
+    int32_t instructions_offset_;
+    bool initialized_;
+    Lock initialization_lock_;
+  };
+
+  virtual ~GlyphTable();
+
+  // C++ port: rename glyph() to GetGlyph().
+  Glyph* GetGlyph(int32_t offset, int32_t length);
+
+ private:
+  struct Offset {
+    enum {
+      // header
+      kNumberOfContours = 0,
+      kXMin = 2,
+      kYMin = 4,
+      kXMax = 6,
+      kYMax = 8,
+
+      // Simple Glyph Description
+      kSimpleEndPtsOfCountours = 10,
+      // offset from the end of the contours array
+      kSimpleInstructionLength = 0,
+      kSimpleInstructions = 2,
+      // flags
+      // xCoordinates
+      // yCoordinates
+
+      // Composite Glyph Description
+      kCompositeFlags = 0,
+      kCompositeGyphIndexWithoutFlag = 0,
+      kCompositeGlyphIndexWithFlag = 2,
+    };
+  };
+
+  GlyphTable(Header* header, ReadableFontData* data);
+};
+typedef Ptr<GlyphTable> GlyphTablePtr;
+typedef Ptr<GlyphTable::Builder> GlyphTableBuilderPtr;
+typedef std::vector<GlyphTableBuilderPtr> GlyphTableBuilderList;
+typedef Ptr<GlyphTable::Glyph> GlyphPtr;
+typedef Ptr<GlyphTable::Glyph::Builder> GlyphBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_TRUETYPE_GLYPH_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/table/truetype/loca_table.cc b/sfntly/cpp/src/sfntly/table/truetype/loca_table.cc
new file mode 100644
index 0000000..c692155
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/truetype/loca_table.cc
@@ -0,0 +1,246 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/table/truetype/loca_table.h"
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+/******************************************************************************
+ * LocaTable class
+ ******************************************************************************/
+LocaTable::~LocaTable() {}
+
+int32_t LocaTable::GlyphOffset(int32_t glyph_id) {
+  if (glyph_id < 0 || glyph_id >= num_glyphs_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException("Glyph ID is out of bounds.");
+#endif
+    return 0;
+  }
+  return Loca(glyph_id);
+}
+
+int32_t LocaTable::GlyphLength(int32_t glyph_id) {
+  if (glyph_id < 0 || glyph_id >= num_glyphs_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException("Glyph ID is out of bounds.");
+#endif
+    return 0;
+  }
+  return Loca(glyph_id + 1) - Loca(glyph_id);
+}
+
+int32_t LocaTable::NumLocas() {
+  return num_glyphs_ + 1;
+}
+
+int32_t LocaTable::Loca(int32_t index) {
+  if (index > num_glyphs_) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundException();
+#endif
+    return 0;
+  }
+  if (format_version_ == IndexToLocFormat::kShortOffset) {
+    return 2 * data_->ReadUShort(index * DataSize::kUSHORT);
+  }
+  return data_->ReadULongAsInt(index * DataSize::kULONG);
+}
+
+LocaTable::LocaTable(Header* header,
+                     ReadableFontData* data,
+                     int32_t format_version,
+                     int32_t num_glyphs)
+    : Table(header, data),
+      format_version_(format_version),
+      num_glyphs_(num_glyphs) {
+}
+
+/******************************************************************************
+ * LocaTable::Iterator class
+ ******************************************************************************/
+LocaTable::LocaIterator::LocaIterator(LocaTable* table)
+    : PODIterator<int32_t, LocaTable>(table), index_(-1) {
+}
+
+bool LocaTable::LocaIterator::HasNext() {
+  return index_ <= container()->num_glyphs_;
+}
+
+int32_t LocaTable::LocaIterator::Next() {
+  return container()->Loca(index_++);
+}
+
+/******************************************************************************
+ * LocaTable::Builder class
+ ******************************************************************************/
+LocaTable::Builder::Builder(Header* header, WritableFontData* data)
+    : Table::Builder(header, data),
+      format_version_(IndexToLocFormat::kLongOffset),
+      num_glyphs_(-1) {
+}
+
+LocaTable::Builder::Builder(Header* header, ReadableFontData* data)
+    : Table::Builder(header, data),
+      format_version_(IndexToLocFormat::kLongOffset),
+      num_glyphs_(-1) {
+}
+
+LocaTable::Builder::~Builder() {}
+
+CALLER_ATTACH
+LocaTable::Builder* LocaTable::Builder::CreateBuilder(Header* header,
+                                                      WritableFontData* data) {
+  Ptr<LocaTable::Builder> builder;
+  builder = new LocaTable::Builder(header, data);
+  return builder.Detach();
+}
+
+IntegerList* LocaTable::Builder::LocaList() {
+  return GetLocaList();
+}
+
+void LocaTable::Builder::SetLocaList(IntegerList* list) {
+  loca_.clear();
+  if (list) {
+    loca_ = *list;
+    set_model_changed();
+  }
+}
+
+int32_t LocaTable::Builder::GlyphOffset(int32_t glyph_id) {
+  if (CheckGlyphRange(glyph_id) == -1) {
+    return 0;
+  }
+  return GetLocaList()->at(glyph_id);
+}
+
+int32_t LocaTable::Builder::GlyphLength(int32_t glyph_id) {
+  if (CheckGlyphRange(glyph_id) == -1) {
+    return 0;
+  }
+  return GetLocaList()->at(glyph_id + 1) - GetLocaList()->at(glyph_id);
+}
+
+void LocaTable::Builder::SetNumGlyphs(int32_t num_glyphs) {
+  num_glyphs_ = num_glyphs;
+}
+
+int32_t LocaTable::Builder::NumGlyphs() {
+  return LastGlyphIndex() - 1;
+}
+
+void LocaTable::Builder::Revert() {
+  loca_.clear();
+  set_model_changed(false);
+}
+
+int32_t LocaTable::Builder::NumLocas() {
+  return GetLocaList()->size();
+}
+
+int32_t LocaTable::Builder::Loca(int32_t index) {
+  return GetLocaList()->at(index);
+}
+
+CALLER_ATTACH
+FontDataTable* LocaTable::Builder::SubBuildTable(ReadableFontData* data) {
+  FontDataTablePtr table =
+      new LocaTable(header(), data, format_version_, num_glyphs_);
+  return table.Detach();
+}
+
+void LocaTable::Builder::SubDataSet() {
+  Initialize(InternalReadData());
+}
+
+int32_t LocaTable::Builder::SubDataSizeToSerialize() {
+  if (loca_.empty()) {
+    return 0;
+  }
+  if (format_version_ == IndexToLocFormat::kLongOffset) {
+    return loca_.size() * DataSize::kULONG;
+  }
+  return loca_.size() * DataSize::kUSHORT;
+}
+
+bool LocaTable::Builder::SubReadyToSerialize() {
+  return !loca_.empty();
+}
+
+int32_t LocaTable::Builder::SubSerialize(WritableFontData* new_data) {
+  int32_t size = 0;
+  for (IntegerList::iterator l = loca_.begin(), end = loca_.end();
+                             l != end; ++l) {
+    if (format_version_ == IndexToLocFormat::kLongOffset) {
+      size += new_data->WriteULong(size, *l);
+    } else {
+      size += new_data->WriteUShort(size, *l / 2);
+    }
+  }
+  num_glyphs_ = loca_.size() - 1;
+  return size;
+}
+
+void LocaTable::Builder::Initialize(ReadableFontData* data) {
+  ClearLoca(false);
+  if (data) {
+    if (NumGlyphs() < 0) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+      throw IllegalStateException("numglyphs not set on LocaTable Builder.");
+#endif
+      return;
+    }
+    LocaTablePtr table =
+        new LocaTable(header(), data, format_version_, num_glyphs_);
+    Ptr<LocaTable::LocaIterator> loca_iter =
+        new LocaTable::LocaIterator(table);
+    while (loca_iter->HasNext()) {
+      loca_.push_back(loca_iter->Next());
+    }
+  }
+}
+
+int32_t LocaTable::Builder::CheckGlyphRange(int32_t glyph_id) {
+  if (glyph_id < 0 || glyph_id > LastGlyphIndex()) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw IndexOutOfBoundsException("Glyph ID is outside of the allowed range");
+#endif
+    return -1;
+  }
+  return glyph_id;
+}
+
+int32_t LocaTable::Builder::LastGlyphIndex() {
+  return !loca_.empty() ? loca_.size() - 2 : num_glyphs_ - 1;
+}
+
+IntegerList* LocaTable::Builder::GetLocaList() {
+  if (loca_.empty()) {
+    Initialize(InternalReadData());
+    set_model_changed();
+  }
+  return &loca_;
+}
+
+void LocaTable::Builder::ClearLoca(bool nullify) {
+  // Note: in C++ port, nullify is not used at all.
+  UNREFERENCED_PARAMETER(nullify);
+  loca_.clear();
+  set_model_changed(false);
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/table/truetype/loca_table.h b/sfntly/cpp/src/sfntly/table/truetype/loca_table.h
new file mode 100644
index 0000000..67c5749
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/table/truetype/loca_table.h
@@ -0,0 +1,183 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TABLE_TRUETYPE_LOCA_TABLE_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TABLE_TRUETYPE_LOCA_TABLE_H_
+
+#include "sfntly/port/java_iterator.h"
+#include "sfntly/table/table.h"
+#include "sfntly/table/core/font_header_table.h"
+
+namespace sfntly {
+
+// A Loca table - 'loca'.
+class LocaTable : public Table, public RefCounted<LocaTable> {
+ public:
+  class LocaIterator : public PODIterator<int32_t, LocaTable> {
+   public:
+    explicit LocaIterator(LocaTable* table);
+    virtual ~LocaIterator() {}
+
+    virtual bool HasNext();
+    virtual int32_t Next();
+
+   private:
+    int32_t index_;
+  };
+
+  class Builder : public Table::Builder, public RefCounted<Builder> {
+   public:
+    // Constructor scope altered to public for base class to instantiate.
+    Builder(Header* header, WritableFontData* data);
+    Builder(Header* header, ReadableFontData* data);
+    virtual ~Builder();
+
+    static CALLER_ATTACH Builder* CreateBuilder(Header* header,
+                                                WritableFontData* data);
+
+    // Get the format version that will be used when the loca table is
+    // generated.
+    // @return the loca table format version
+    int32_t format_version() { return format_version_; }
+    void set_format_version(int32_t value) { format_version_ = value; }
+
+    // Gets the List of locas for loca table builder. These may be manipulated
+    // in any way by the caller and the changes will be reflected in the final
+    // loca table produced as long as no subsequent call is made to the
+    // SetLocaList(List) method.
+    // If there is no current data for the loca table builder or the loca list
+    // have not been previously set then this will return an empty List.
+    IntegerList* LocaList();
+
+    // Set the list of locas to be used for building this table. If any existing
+    // list was already retrieved with the LocaList() method then the
+    // connection of that previous list to this builder will be broken.
+    void SetLocaList(IntegerList* list);
+
+    // Return the offset for the given glyph id. Valid glyph ids are from 0 to
+    // one less than the number of glyphs. The zero entry is the special entry
+    // for the notdef glyph. The final entry beyond the last glyph id is used to
+    // calculate the size of the last glyph.
+    // @param glyphId the glyph id to get the offset for; must be less than or
+    //        equal to one more than the number of glyph ids
+    // @return the offset in the glyph table to the specified glyph id
+    int32_t GlyphOffset(int32_t glyph_id);
+
+    // Get the length of the data in the glyph table for the specified glyph id.
+    int32_t GlyphLength(int32_t glyph_id);
+
+    // Set the number of glyphs.
+    // This method sets the number of glyphs that the builder will attempt to
+    // parse location data for from the raw binary data. This method only needs
+    // to be called (and <b>must</b> be) when the raw data for this builder has
+    // been changed. It does not by itself reset the data or clear any set loca
+    // list.
+    void SetNumGlyphs(int32_t num_glyphs);
+
+    // Get the number of glyphs that this builder has support for.
+    int NumGlyphs();
+
+    // Revert the loca table builder to the state contained in the last raw data
+    // set on the builder. That raw data may be that read from a font file when
+    // the font builder was created, that set by a user of the loca table
+    // builder, or null data if this builder was created as a new empty builder.
+    void Revert();
+
+    // Get the number of locations or locas. This will be one more than the
+    // number of glyphs for this table since the last loca position is used to
+    // indicate the size of the final glyph.
+    int32_t NumLocas();
+
+    // Get the value from the loca table for the index specified. These are the
+    // raw values from the table that are used to compute the offset and size of
+    // a glyph in the glyph table. Valid index values run from 0 to the number
+    // of glyphs in the font.
+    int32_t Loca(int32_t index);
+
+    virtual CALLER_ATTACH FontDataTable* SubBuildTable(ReadableFontData* data);
+    virtual void SubDataSet();
+    virtual int32_t SubDataSizeToSerialize();
+    virtual bool SubReadyToSerialize();
+    virtual int32_t SubSerialize(WritableFontData* new_data);
+
+   private:
+    // Initialize the internal state from the data. Done lazily since in many
+    // cases the builder will be just creating a table object with no parsing
+    // required.
+    // @param data the data to initialize from
+    void Initialize(ReadableFontData* data);
+
+    // Checks that the glyph id is within the correct range.
+    // @return glyph_id if correct, -1 otherwise.
+    int32_t CheckGlyphRange(int32_t glyph_id);
+
+    int32_t LastGlyphIndex();
+
+    // Internal method to get the loca list if already generated and if not to
+    // initialize the state of the builder.
+    // @return the loca list
+    IntegerList* GetLocaList();
+
+    void ClearLoca(bool nullify);
+
+    int32_t format_version_;  // Note: IndexToLocFormat
+    int32_t num_glyphs_;
+    IntegerList loca_;
+  };
+
+  virtual ~LocaTable();
+
+  int32_t format_version() { return format_version_; }
+  int32_t num_glyphs() { return num_glyphs_; }
+
+  // Return the offset for the given glyph id. Valid glyph ids are from 0 to the
+  // one less than the number of glyphs. The zero entry is the special entry for
+  // the notdef glyph. The final entry beyond the last glyph id is used to
+  // calculate the size of the last glyph.
+  // @param glyphId the glyph id to get the offset for; must be less than or
+  //        equal to one more than the number of glyph ids
+  // @return the offset in the glyph table to the specified glyph id
+  int32_t GlyphOffset(int32_t glyph_id);
+
+  // Get the length of the data in the glyph table for the specified glyph id.
+  int32_t GlyphLength(int32_t glyph_id);
+
+  // Get the number of locations or locas. This will be one more than the number
+  // of glyphs for this table since the last loca position is used to indicate
+  // the size of the final glyph.
+  int32_t NumLocas();
+
+  // Get the value from the loca table for the index specified. Valid index
+  // values run from 0 to the number of glyphs in the font.
+  int32_t Loca(int32_t index);
+
+ private:
+  LocaTable(Header* header,
+            ReadableFontData* data,
+            int32_t format_version,
+            int32_t num_glyphs);
+
+  int32_t format_version_;  // Note: Java's version, renamed to format_version_
+  int32_t num_glyphs_;
+
+  friend class LocaIterator;
+};
+typedef Ptr<LocaTable> LocaTablePtr;
+typedef Ptr<LocaTable::Builder> LocaTableBuilderPtr;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TABLE_TRUETYPE_LOCA_TABLE_H_
diff --git a/sfntly/cpp/src/sfntly/tag.cc b/sfntly/cpp/src/sfntly/tag.cc
new file mode 100644
index 0000000..c9d8c29
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tag.cc
@@ -0,0 +1,110 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/tag.h"
+#include "sfntly/port/endian.h"
+
+// Use a macro instead of GenerateTag() because gcc 4.4.3 creates static
+// initializers in that case.
+#define TAG(a, b, c, d) ((a << 24) | (b << 16) | (c << 8) | d);
+
+namespace sfntly {
+
+const int32_t Tag::ttcf = TAG('t', 't', 'c', 'f');
+const int32_t Tag::cmap = TAG('c', 'm', 'a', 'p');
+const int32_t Tag::head = TAG('h', 'e', 'a', 'd');
+const int32_t Tag::hhea = TAG('h', 'h', 'e', 'a');
+const int32_t Tag::hmtx = TAG('h', 'm', 't', 'x');
+const int32_t Tag::maxp = TAG('m', 'a', 'x', 'p');
+const int32_t Tag::name = TAG('n', 'a', 'm', 'e');
+const int32_t Tag::OS_2 = TAG('O', 'S', '/', '2');
+const int32_t Tag::post = TAG('p', 'o', 's', 't');
+const int32_t Tag::cvt  = TAG('c', 'v', 't', ' ');
+const int32_t Tag::fpgm = TAG('f', 'p', 'g', 'm');
+const int32_t Tag::glyf = TAG('g', 'l', 'y', 'f');
+const int32_t Tag::loca = TAG('l', 'o', 'c', 'a');
+const int32_t Tag::prep = TAG('p', 'r', 'e', 'p');
+const int32_t Tag::CFF  = TAG('C', 'F', 'F', ' ');
+const int32_t Tag::VORG = TAG('V', 'O', 'R', 'G');
+const int32_t Tag::EBDT = TAG('E', 'B', 'D', 'T');
+const int32_t Tag::EBLC = TAG('E', 'B', 'L', 'C');
+const int32_t Tag::EBSC = TAG('E', 'B', 'S', 'C');
+const int32_t Tag::BASE = TAG('B', 'A', 'S', 'E');
+const int32_t Tag::GDEF = TAG('G', 'D', 'E', 'F');
+const int32_t Tag::GPOS = TAG('G', 'P', 'O', 'S');
+const int32_t Tag::GSUB = TAG('G', 'S', 'U', 'B');
+const int32_t Tag::JSTF = TAG('J', 'S', 'T', 'F');
+const int32_t Tag::DSIG = TAG('D', 'S', 'I', 'G');
+const int32_t Tag::gasp = TAG('g', 'a', 's', 'p');
+const int32_t Tag::hdmx = TAG('h', 'd', 'm', 'x');
+const int32_t Tag::kern = TAG('k', 'e', 'r', 'n');
+const int32_t Tag::LTSH = TAG('L', 'T', 'S', 'H');
+const int32_t Tag::PCLT = TAG('P', 'C', 'L', 'T');
+const int32_t Tag::VDMX = TAG('V', 'D', 'M', 'X');
+const int32_t Tag::vhea = TAG('v', 'h', 'e', 'a');
+const int32_t Tag::vmtx = TAG('v', 'm', 't', 'x');
+const int32_t Tag::bsln = TAG('b', 's', 'l', 'n');
+const int32_t Tag::feat = TAG('f', 'e', 'a', 't');
+const int32_t Tag::lcar = TAG('l', 'c', 'a', 'r');
+const int32_t Tag::morx = TAG('m', 'o', 'r', 'x');
+const int32_t Tag::opbd = TAG('o', 'p', 'b', 'd');
+const int32_t Tag::prop = TAG('p', 'r', 'o', 'p');
+const int32_t Tag::Feat = TAG('F', 'e', 'a', 't');
+const int32_t Tag::Glat = TAG('G', 'l', 'a', 't');
+const int32_t Tag::Gloc = TAG('G', 'l', 'o', 'c');
+const int32_t Tag::Sile = TAG('S', 'i', 'l', 'e');
+const int32_t Tag::Silf = TAG('S', 'i', 'l', 'f');
+const int32_t Tag::bhed = TAG('b', 'h', 'e', 'd');
+const int32_t Tag::bdat = TAG('b', 'd', 'a', 't');
+const int32_t Tag::bloc = TAG('b', 'l', 'o', 'c');
+
+const int32_t CFF_TABLE_ORDERING[] = {
+    Tag::head,
+    Tag::hhea,
+    Tag::maxp,
+    Tag::OS_2,
+    Tag::name,
+    Tag::cmap,
+    Tag::post,
+    Tag::CFF };
+const size_t CFF_TABLE_ORDERING_SIZE =
+    sizeof(CFF_TABLE_ORDERING) / sizeof(int32_t);
+
+const int32_t TRUE_TYPE_TABLE_ORDERING[] = {
+    Tag::head,
+    Tag::hhea,
+    Tag::maxp,
+    Tag::OS_2,
+    Tag::hmtx,
+    Tag::LTSH,
+    Tag::VDMX,
+    Tag::hdmx,
+    Tag::cmap,
+    Tag::fpgm,
+    Tag::prep,
+    Tag::cvt,
+    Tag::loca,
+    Tag::glyf,
+    Tag::kern,
+    Tag::name,
+    Tag::post,
+    Tag::gasp,
+    Tag::PCLT,
+    Tag::DSIG };
+const size_t TRUE_TYPE_TABLE_ORDERING_SIZE =
+    sizeof(TRUE_TYPE_TABLE_ORDERING) / sizeof(int32_t);
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/tag.h b/sfntly/cpp/src/sfntly/tag.h
new file mode 100644
index 0000000..0ecbab8
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tag.h
@@ -0,0 +1,123 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TAG_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TAG_H_
+
+#include <cstddef>
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+// Font identification tags used for tables, features, etc.
+// Tag names are consistent with the OpenType and sfnt specs.
+struct Tag {
+  static const int32_t ttcf;
+
+  // Table Type Tags
+  // required tables
+  static const int32_t cmap;
+  static const int32_t head;
+  static const int32_t hhea;
+  static const int32_t hmtx;
+  static const int32_t maxp;
+  static const int32_t name;
+  static const int32_t OS_2;
+  static const int32_t post;
+
+  // TrueType outline tables
+  static const int32_t cvt;
+  static const int32_t fpgm;
+  static const int32_t glyf;
+  static const int32_t loca;
+  static const int32_t prep;
+
+  // PostScript outline tables
+  static const int32_t CFF;
+  static const int32_t VORG;
+
+  // opentype bitmap glyph outlines
+  static const int32_t EBDT;
+  static const int32_t EBLC;
+  static const int32_t EBSC;
+
+  // advanced typographic features
+  static const int32_t BASE;
+  static const int32_t GDEF;
+  static const int32_t GPOS;
+  static const int32_t GSUB;
+  static const int32_t JSTF;
+
+  // other
+  static const int32_t DSIG;
+  static const int32_t gasp;
+  static const int32_t hdmx;
+  static const int32_t kern;
+  static const int32_t LTSH;
+  static const int32_t PCLT;
+  static const int32_t VDMX;
+  static const int32_t vhea;
+  static const int32_t vmtx;
+
+  // AAT tables
+  static const int32_t bsln;
+  static const int32_t feat;
+  static const int32_t lcar;
+  static const int32_t morx;
+  static const int32_t opbd;
+  static const int32_t prop;
+
+  // Graphite tables
+  static const int32_t Feat;
+  static const int32_t Glat;
+  static const int32_t Gloc;
+  static const int32_t Sile;
+  static const int32_t Silf;
+
+  // truetype bitmap font tables
+  static const int32_t bhed;
+  static const int32_t bdat;
+  static const int32_t bloc;
+};
+
+// Create integer tag value for human readable tag name.
+inline int32_t GenerateTag(int32_t a, int32_t b, int32_t c, int32_t d) {
+  return (a << 24) | (b << 16) | (c << 8) | d;
+}
+
+// Translate tag to human readable string.
+// The Caller must delete[] the returned value.
+inline char* TagToString(int32_t tag) {
+  char *name = new char[5];
+  name[0] = static_cast<char>((tag & 0xff000000) >> 24);
+  name[1] = static_cast<char>((tag & 0x00ff0000) >> 16);
+  name[2] = static_cast<char>((tag & 0x0000ff00) >> 8);
+  name[3] = static_cast<char>(tag & 0x000000ff);
+  name[4] = 0;
+  return name;
+}
+
+// Note: For Java, these two orderings are in Font class.  Moved here to avoid
+//       VC++ bug of not populating correct values.
+extern const int32_t CFF_TABLE_ORDERING[];
+extern const size_t CFF_TABLE_ORDERING_SIZE;
+extern const int32_t TRUE_TYPE_TABLE_ORDERING[];
+extern const size_t TRUE_TYPE_TABLE_ORDERING_SIZE;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TAG_H_
diff --git a/sfntly/cpp/src/sfntly/tools/subsetter/glyph_table_subsetter.cc b/sfntly/cpp/src/sfntly/tools/subsetter/glyph_table_subsetter.cc
new file mode 100644
index 0000000..b3d6b07
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tools/subsetter/glyph_table_subsetter.cc
@@ -0,0 +1,90 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/tools/subsetter/glyph_table_subsetter.h"
+
+#include "sfntly/table/truetype/glyph_table.h"
+#include "sfntly/table/truetype/loca_table.h"
+#include "sfntly/tag.h"
+#include "sfntly/tools/subsetter/subsetter.h"
+#include "sfntly/port/exception_type.h"
+
+namespace sfntly {
+
+const int32_t kGlyphTableSubsetterTags[2] = {Tag::glyf, Tag::loca};
+
+GlyphTableSubsetter::GlyphTableSubsetter()
+    : TableSubsetterImpl(kGlyphTableSubsetterTags, 2) {
+}
+
+GlyphTableSubsetter::~GlyphTableSubsetter() {}
+
+bool GlyphTableSubsetter::Subset(Subsetter* subsetter,
+                                 Font* font,
+                                 Font::Builder* font_builder) {
+  assert(font);
+  assert(subsetter);
+  assert(font_builder);
+
+  IntegerList* permutation_table = subsetter->GlyphPermutationTable();
+  if (!permutation_table || permutation_table->empty())
+    return false;
+
+  GlyphTablePtr glyph_table = down_cast<GlyphTable*>(font->GetTable(Tag::glyf));
+  LocaTablePtr loca_table = down_cast<LocaTable*>(font->GetTable(Tag::loca));
+  if (glyph_table == NULL || loca_table == NULL) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw RuntimeException("Font to subset is not valid.");
+#endif
+    return false;
+  }
+
+  GlyphTableBuilderPtr glyph_table_builder =
+      down_cast<GlyphTable::Builder*>
+      (font_builder->NewTableBuilder(Tag::glyf));
+  LocaTableBuilderPtr loca_table_builder =
+      down_cast<LocaTable::Builder*>
+      (font_builder->NewTableBuilder(Tag::loca));
+  if (glyph_table_builder == NULL || loca_table_builder == NULL) {
+#if !defined (SFNTLY_NO_EXCEPTION)
+    throw RuntimeException("Builder for subset is not valid.");
+#endif
+    return false;
+  }
+  GlyphTable::GlyphBuilderList* glyph_builders =
+      glyph_table_builder->GlyphBuilders();
+  for (IntegerList::iterator old_glyph_id = permutation_table->begin(),
+                             old_glyph_id_end = permutation_table->end();
+                             old_glyph_id != old_glyph_id_end; ++old_glyph_id) {
+    int old_offset = loca_table->GlyphOffset(*old_glyph_id);
+    int old_length = loca_table->GlyphLength(*old_glyph_id);
+    GlyphPtr glyph;
+    glyph.Attach(glyph_table->GetGlyph(old_offset, old_length));
+    ReadableFontDataPtr data = glyph->ReadFontData();
+    WritableFontDataPtr copy_data;
+    copy_data.Attach(WritableFontData::CreateWritableFontData(data->Length()));
+    data->CopyTo(copy_data);
+    GlyphBuilderPtr glyph_builder;
+    glyph_builder.Attach(glyph_table_builder->GlyphBuilder(copy_data));
+    glyph_builders->push_back(glyph_builder);
+  }
+  IntegerList loca_list;
+  glyph_table_builder->GenerateLocaList(&loca_list);
+  loca_table_builder->SetLocaList(&loca_list);
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/tools/subsetter/glyph_table_subsetter.h b/sfntly/cpp/src/sfntly/tools/subsetter/glyph_table_subsetter.h
new file mode 100644
index 0000000..88c7044
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tools/subsetter/glyph_table_subsetter.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_GLYPH_TABLE_SUBSETTER_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_GLYPH_TABLE_SUBSETTER_H_
+
+#include "sfntly/tools/subsetter/table_subsetter_impl.h"
+
+namespace sfntly {
+
+class GlyphTableSubsetter : public TableSubsetterImpl,
+                            public RefCounted<GlyphTableSubsetter> {
+ public:
+  GlyphTableSubsetter();
+  virtual ~GlyphTableSubsetter();
+
+  virtual bool Subset(Subsetter* subsetter,
+                      Font* font,
+                      Font::Builder* font_builder);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_GLYPH_TABLE_SUBSETTER_H_
diff --git a/sfntly/cpp/src/sfntly/tools/subsetter/subsetter.cc b/sfntly/cpp/src/sfntly/tools/subsetter/subsetter.cc
new file mode 100644
index 0000000..7d98779
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tools/subsetter/subsetter.cc
@@ -0,0 +1,102 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/tools/subsetter/subsetter.h"
+
+#include <algorithm>
+#include <iterator>
+
+#include "sfntly/tools/subsetter/glyph_table_subsetter.h"
+
+namespace sfntly {
+
+Subsetter::Subsetter(Font* font, FontFactory* font_factory) {
+  font_ = font;
+  font_factory_ = font_factory;
+  TableSubsetterPtr subsetter = new GlyphTableSubsetter();
+  // TODO(arthurhsu): IMPLEMENT: CMap table subsetter
+  table_subsetters_.push_back(subsetter);
+}
+
+Subsetter::~Subsetter() {
+  font_factory_.Release();
+  font_.Release();
+  table_subsetters_.clear();
+}
+
+void Subsetter::SetGlyphs(IntegerList* glyphs) {
+  new_to_old_glyphs_ = *glyphs;
+}
+
+void Subsetter::SetCMaps(CMapIdList* cmap_ids, int32_t number) {
+  UNREFERENCED_PARAMETER(cmap_ids);
+  UNREFERENCED_PARAMETER(number);
+  // TODO(arthurhsu): IMPLEMENT
+}
+
+void Subsetter::SetRemoveTables(IntegerSet* remove_tables) {
+  remove_tables_ = *remove_tables;
+}
+
+CALLER_ATTACH Font::Builder* Subsetter::Subset() {
+  FontBuilderPtr font_builder;
+  font_builder.Attach(font_factory_->NewFontBuilder());
+
+  IntegerSet table_tags;
+  for (TableMap::const_iterator i = font_->GetTableMap()->begin(),
+                                e = font_->GetTableMap()->end(); i != e; ++i) {
+    table_tags.insert(i->first);
+  }
+  if (!remove_tables_.empty()) {
+    IntegerSet result;
+    std::set_difference(table_tags.begin(), table_tags.end(),
+                        remove_tables_.begin(), remove_tables_.end(),
+                        std::inserter(result, result.end()));
+    table_tags = result;
+  }
+  for (TableSubsetterList::iterator
+           table_subsetter = table_subsetters_.begin(),
+           table_subsetter_end = table_subsetters_.end();
+           table_subsetter != table_subsetter_end; ++table_subsetter) {
+    bool handled = (*table_subsetter)->Subset(this, font_, font_builder);
+    if (handled) {
+      IntegerSet* handled_tags = (*table_subsetter)->TagsHandled();
+      IntegerSet result;
+      std::set_difference(table_tags.begin(), table_tags.end(),
+                          handled_tags->begin(), handled_tags->end(),
+                          std::inserter(result, result.end()));
+      table_tags = result;
+    }
+  }
+  for (IntegerSet::iterator tag = table_tags.begin(),
+                            tag_end = table_tags.end(); tag != tag_end; ++tag) {
+    Table* table = font_->GetTable(*tag);
+    if (table) {
+      font_builder->NewTableBuilder(*tag, table->ReadFontData());
+    }
+  }
+  return font_builder.Detach();
+}
+
+IntegerList* Subsetter::GlyphPermutationTable() {
+  return &new_to_old_glyphs_;
+}
+
+CMapIdList* Subsetter::CMapId() {
+  return &cmap_ids_;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/tools/subsetter/subsetter.h b/sfntly/cpp/src/sfntly/tools/subsetter/subsetter.h
new file mode 100644
index 0000000..85940a7
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tools/subsetter/subsetter.h
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_SUBSETTER_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_SUBSETTER_H_
+
+#include <vector>
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/tools/subsetter/table_subsetter.h"
+
+namespace sfntly {
+
+class Subsetter : public RefCounted<Subsetter> {
+ public:
+  Subsetter(Font* font, FontFactory* font_factory);
+  virtual ~Subsetter();
+
+  virtual void SetGlyphs(IntegerList* glyphs);
+
+  // Set the cmaps to be used in the subsetted font. The cmaps are listed in
+  // order of priority and the number parameter gives a count of how many of the
+  // list should be put into the subsetted font. If there are no matches in the
+  // font for any of the provided cmap ids which would lead to a font with no
+  // cmap then an error will be thrown during subsetting.
+  // The two most common cases would be: <list>
+  // * a list of one or more cmap ids with a count setting of 1
+  //     This will use the list of cmap ids as an ordered priority and look for
+  //     an available cmap in the font that matches the requests. Only the first
+  //     such match will be placed in the subsetted font.
+  // * a list of one or more cmap ids with a count setting equal to the list
+  //   length
+  //     This will use the list of cmap ids and try to place each one specified
+  //     into the subsetted font.
+  // @param cmapIds the cmap ids to use for the subsetted font
+  // @param number the maximum number of cmaps to place in the subsetted font
+  virtual void SetCMaps(CMapIdList* cmap_ids, int32_t number);
+
+  virtual void SetRemoveTables(IntegerSet* remove_tables);
+  virtual CALLER_ATTACH Font::Builder* Subset();
+  virtual IntegerList* GlyphPermutationTable();
+  virtual CMapIdList* CMapId();
+
+ private:
+  FontPtr font_;
+  FontFactoryPtr font_factory_;
+  TableSubsetterList table_subsetters_;
+
+  // Settings from user
+  IntegerSet remove_tables_;
+  IntegerList new_to_old_glyphs_;
+  CMapIdList cmap_ids_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_SUBSETTER_H_
diff --git a/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter.h b/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter.h
new file mode 100644
index 0000000..1336615
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter.h
@@ -0,0 +1,39 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_TABLE_SUBSETTER_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_TABLE_SUBSETTER_H_
+
+#include <vector>
+
+#include "sfntly/font.h"
+
+namespace sfntly {
+
+class Subsetter;
+class TableSubsetter : virtual public RefCount {
+ public:
+  virtual IntegerSet* TagsHandled() = 0;
+  virtual bool TagHandled(int32_t tag) = 0;
+  virtual bool Subset(Subsetter* subsetter, Font* font,
+                      Font::Builder* font_builder) = 0;
+};
+typedef Ptr<TableSubsetter> TableSubsetterPtr;
+typedef std::vector<TableSubsetterPtr> TableSubsetterList;
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_TABLE_SUBSETTER_H_
diff --git a/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter_impl.cc b/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter_impl.cc
new file mode 100644
index 0000000..f239c78
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter_impl.cc
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/tools/subsetter/table_subsetter_impl.h"
+
+namespace sfntly {
+
+TableSubsetterImpl::TableSubsetterImpl(const int32_t* tags,
+                                       size_t tags_length) {
+  for (size_t i = 0; i < tags_length; ++i) {
+    tags_.insert(tags[i]);
+  }
+}
+
+TableSubsetterImpl::~TableSubsetterImpl() {}
+
+bool TableSubsetterImpl::TagHandled(int32_t tag) {
+  return tags_.find(tag) != tags_.end();
+}
+
+IntegerSet* TableSubsetterImpl::TagsHandled() {
+  return &tags_;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter_impl.h b/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter_impl.h
new file mode 100644
index 0000000..de0d9a9
--- /dev/null
+++ b/sfntly/cpp/src/sfntly/tools/subsetter/table_subsetter_impl.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_TABLE_SUBSETTER_IMPL_H_
+#define SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_TABLE_SUBSETTER_IMPL_H_
+
+#include "sfntly/tools/subsetter/table_subsetter.h"
+
+namespace sfntly {
+
+class TableSubsetterImpl : public TableSubsetter {
+ public:
+  TableSubsetterImpl(const int32_t* tags, size_t tags_length);
+  virtual ~TableSubsetterImpl();
+  virtual bool TagHandled(int32_t tag);
+  virtual IntegerSet* TagsHandled();
+
+ protected:
+  IntegerSet tags_;
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_SFNTLY_TOOLS_SUBSETTER_TABLE_SUBSETTER_IMPL_H_
diff --git a/sfntly/cpp/src/test/autogenerated/cmap_basic_test.cc b/sfntly/cpp/src/test/autogenerated/cmap_basic_test.cc
new file mode 100644
index 0000000..aae35e1
--- /dev/null
+++ b/sfntly/cpp/src/test/autogenerated/cmap_basic_test.cc
@@ -0,0 +1,131 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// type.h needs to be included first because of building issues on Windows
+// Type aliases we delcare are defined in other headers and make the build
+// fail otherwise.
+#include "sfntly/port/type.h"
+#include <assert.h>
+#include <stdio.h>
+#include <unicode/ucnv.h>
+
+#include <iostream>
+#include <string>
+
+#include "gtest/gtest.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/table/core/font_header_table.h"
+#include "sfntly/tag.h"
+#include "test/autogenerated/cmap_test_data.h"
+#include "test/test_font_utils.h"
+#include "test/test_utils.h"
+#include "test/test_xml_utils.h"
+
+namespace sfntly {
+
+#if GTEST_HAS_PARAM_TEST
+
+using ::testing::TestWithParam;
+using ::testing::Values;
+
+class CMapBasicTests : public :: testing::TestWithParam<const char*> {
+ public:
+  CMapBasicTests() {}
+  virtual void SetUp();
+  virtual void TearDown() {}
+
+  Ptr<CMapTable> cmap_table_;
+  TiXmlDocument document_;
+};
+
+void CMapBasicTests::SetUp() {
+  // Loading the font
+  Ptr<FontFactory> font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  FontArray font_array;
+  std::string font_name = "../../";
+#if defined (WIN32)
+  font_name += "../";
+#endif
+  font_name += std::string(GetParam());
+  LoadFont(font_name.c_str(), font_factory, &font_array);
+  ASSERT_FALSE(font_array.empty());
+  Ptr<Font> font = font_array.at(0);
+  ASSERT_NE(font, reinterpret_cast<Font*>(NULL));
+  cmap_table_ = down_cast<CMapTable*>(font->GetTable(Tag::cmap));
+  if (!cmap_table_)
+    fprintf(stderr, "No CMap: %s\n", font_name.c_str());
+  ASSERT_NE(cmap_table_, reinterpret_cast<CMapTable*>(NULL));
+
+  // Loading the XML file
+  document_ = TiXmlDocument((font_name + ".xml").c_str());
+  ASSERT_TRUE(document_.LoadFile());
+}
+
+TEST_P(CMapBasicTests, BasicTest) {
+  TiXmlNodeVector* cmap_table = GetNodesWithName(&document_, "cmap_table");
+  // A font can only have one CMap table
+  ASSERT_EQ(cmap_table->size(), (size_t)1);
+  TiXmlNodeVector* cmaps = GetNodesWithName(cmap_table->at(0), "cmap");
+  const TiXmlAttribute* num_cmaps_attr = GetAttribute(cmap_table->at(0),
+                                                      "num_cmaps");
+  ASSERT_NE(num_cmaps_attr, reinterpret_cast<TiXmlAttribute*>(NULL));
+  // But there may be more than one CMap in this table
+  ASSERT_LE(cmaps->size(), (size_t)num_cmaps_attr->IntValue());
+  for (TiXmlNodeVector::iterator it = cmaps->begin();
+       it != cmaps->end(); ++it) {
+    int32_t platform_id = GetAttribute(*it, "platform_id")->IntValue();
+    int32_t encoding_id = GetAttribute(*it, "encoding_id")->IntValue();
+    Ptr<CMapTable::CMap> cmap;
+    cmap.Attach(cmap_table_->GetCMap(platform_id, encoding_id));
+    if (!cmap) {
+      fprintf(stderr, "Cannot test unsupported CMapFormat%d\n",
+              GetAttribute(*it, "format")->IntValue());
+      continue;
+    }
+    ASSERT_EQ(cmap->platform_id(), platform_id);
+    ASSERT_EQ(cmap->encoding_id(), encoding_id);
+    TiXmlNodeVector* maps = GetNodesWithName(*it, "map");
+    for (TiXmlNodeVector::iterator jt = maps->begin();
+         jt != maps->end(); ++jt) {
+      int32_t character;
+#if defined (WIN32)
+      sscanf_s(GetAttribute(*jt, "char")->Value(), "%x", &character);
+#else
+      sscanf(GetAttribute(*jt, "char")->Value(), "%x", &character);
+#endif
+      int32_t glyph_id = GetAttribute(*jt, "gid")->IntValue();
+      ASSERT_EQ(cmap->GlyphId(character), glyph_id);
+    }
+    delete maps;
+  }
+  delete cmaps;
+  delete cmap_table;
+}
+
+INSTANTIATE_TEST_CASE_P(CMapBasicTests,
+                        CMapBasicTests,
+                        ::testing::ValuesIn(cmap_test_data::kAllTests));
+
+#else
+
+TEST(DummyTest, ValueParameterizedTestsAreNotSupportedOnThisPlatform) {}
+
+#endif  // GTEST_HAS_PARAM
+}
diff --git a/sfntly/cpp/src/test/autogenerated/cmap_test_data.h b/sfntly/cpp/src/test/autogenerated/cmap_test_data.h
new file mode 100644
index 0000000..4a9f267
--- /dev/null
+++ b/sfntly/cpp/src/test/autogenerated/cmap_test_data.h
@@ -0,0 +1,185 @@
+/*
+ * !!! DO NOT EDIT !!!
+ * THIS FILE IS GENERATED BY A SCRIPT.
+ * FOR MORE DETAILS SEE 'README-test_data.txt'.
+ */
+
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TYPOGRAPHY_FONT_SFNTLY_SRC_TEST_AUTOGENERATED_CMAP_TEST_DATA_H_
+#define TYPOGRAPHY_FONT_SFNTLY_SRC_TEST_AUTOGENERATED_CMAP_TEST_DATA_H_
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+namespace cmap_test_data {
+const char* kAllTests[] = {
+  "data/fonts/cousine/Cousine-BoldItalic.ttf",
+  "data/fonts/cousine/Cousine-Bold.ttf",
+  "data/fonts/cousine/Cousine-Regular.ttf",
+  "data/fonts/cousine/Cousine-Italic.ttf",
+  "data/fonts/cedarvillecursive/Cedarville-Cursive.ttf",
+  "data/fonts/dancingscript/DancingScript-Bold.ttf",
+  "data/fonts/dancingscript/DancingScript-Regular.ttf",
+  "data/fonts/damion/Damion-Regular.ttf",
+  "data/fonts/annieuseyourtelescope/AnnieUseYourTelescope.ttf",
+  "data/fonts/deliusswashcaps/DeliusSwashCaps-Regular.ttf",
+  "data/fonts/delius/Delius-Regular.ttf",
+  "data/fonts/coveredbyyourgrace/CoveredByYourGrace.ttf",
+  "data/fonts/ebgaramond/EBGaramond-Regular.ttf",
+  "data/fonts/cabinsketch/CabinSketch-Bold.ttf",
+  "data/fonts/allan/Allan-Bold.ttf",
+  "data/fonts/coda/Coda-Caption-Heavy.ttf",
+  "data/fonts/coda/Coda-Heavy.ttf",
+  "data/fonts/forum/Forum-Regular.ttf",
+  "data/fonts/alike/Alike-Regular.ttf",
+  "data/fonts/corben/Corben-Bold.ttf",
+  "data/fonts/caudex/Caudex-Regular.ttf",
+  "data/fonts/caudex/Caudex-BoldItalic.ttf",
+  "data/fonts/caudex/Caudex-Italic.ttf",
+  "data/fonts/caudex/Caudex-Bold.ttf",
+  "data/fonts/cabin/Cabin-MediumItalic.ttf",
+  "data/fonts/cabin/Cabin-SemiBold.ttf",
+  "data/fonts/cabin/Cabin-SemiBoldItalic.ttf",
+  "data/fonts/cabin/Cabin-BoldItalic.ttf",
+  "data/fonts/cabin/Cabin-Medium.ttf",
+  "data/fonts/cabin/Cabin-Italic.ttf",
+  "data/fonts/cabin/Cabin-Bold.ttf",
+  "data/fonts/cabin/Cabin-Regular.ttf",
+  "data/fonts/dawningofanewday/DawningofaNewDay.ttf",
+  "data/fonts/dangrek/Dangrek.ttf",
+  "data/fonts/blackopsone/BlackOpsOne.ttf",
+  "data/fonts/francoisone/FrancoisOne.ttf",
+  "data/fonts/bowlbyone/BowlbyOne.ttf",
+  "data/fonts/bowlbyone/BowlbyOneSC.ttf",
+  "data/fonts/calligraffiti/Calligraffiti.ttf",
+  "data/fonts/bangers/Bangers.ttf",
+  "data/fonts/astloch/Astloch-Regular.ttf",
+  "data/fonts/astloch/Astloch-Bold.ttf",
+  "data/fonts/angkor/Angkor.ttf",
+  "data/fonts/abrilfatface/AbrilFatface-Regular.ttf",
+  "data/fonts/cantarell/Cantarell-BoldOblique.ttf",
+  "data/fonts/cantarell/Cantarell-Oblique.ttf",
+  "data/fonts/cantarell/Cantarell-Bold.ttf",
+  "data/fonts/cantarell/Cantarell-Regular.ttf",
+  "data/fonts/arvo/Arvo-Bold.ttf",
+  "data/fonts/arvo/Arvo-Italic.ttf",
+  "data/fonts/arvo/Arvo-BoldItalic.ttf",
+  "data/fonts/arvo/Arvo-Regular.ttf",
+  "data/fonts/chewy/Chewy.ttf",
+  "data/fonts/bigshotone/BigshotOne.ttf",
+  "data/fonts/chenla/Chenla.ttf",
+  "data/fonts/bayon/Bayon.ttf",
+  "data/fonts/coustard/Coustard-Black.ttf",
+  "data/fonts/coustard/Coustard-Regular.ttf",
+  "data/fonts/amaticsc/AmaticSC-Bold.ttf",
+  "data/fonts/amaticsc/AmaticSC-Regular.ttf",
+  "data/fonts/comfortaa/Comfortaa-Light.ttf",
+  "data/fonts/comfortaa/Comfortaa-Bold.ttf",
+  "data/fonts/comfortaa/Comfortaa-Regular.ttf",
+  "data/fonts/expletussans/ExpletusSans-Bold.ttf",
+  "data/fonts/expletussans/ExpletusSans-MediumItalic.ttf",
+  "data/fonts/expletussans/ExpletusSans-Medium.ttf",
+  "data/fonts/expletussans/ExpletusSans-SemiBold.ttf",
+  "data/fonts/expletussans/ExpletusSans-Regular.ttf",
+  "data/fonts/expletussans/ExpletusSans-Italic.ttf",
+  "data/fonts/expletussans/ExpletusSans-SemiBoldItalic.ttf",
+  "data/fonts/expletussans/ExpletusSans-BoldItalic.ttf",
+  "data/fonts/aubrey/Aubrey-Regular.ttf",
+  "data/fonts/antic/Antic-Regular.ttf",
+  "data/fonts/copse/Copse-Regular.ttf",
+  "data/fonts/daysone/DaysOne-Regular.ttf",
+  "data/fonts/actor/Actor-Regular.ttf",
+  "data/fonts/bentham/Bentham-Regular.ttf",
+  "data/fonts/federo/Federo-Regular.ttf",
+  "data/fonts/arimo/Arimo-Italic.ttf",
+  "data/fonts/arimo/Arimo-BoldItalic.ttf",
+  "data/fonts/arimo/Arimo-Bold.ttf",
+  "data/fonts/arimo/Arimo-Regular.ttf",
+  "data/fonts/felltypes/IMFeDPsc28P.ttf",
+  "data/fonts/felltypes/IMFeGPrm28P.ttf",
+  "data/fonts/felltypes/IMFeENsc28P.ttf",
+  "data/fonts/felltypes/IMFePIit28P.ttf",
+  "data/fonts/felltypes/IMFeDPrm28P.ttf",
+  "data/fonts/felltypes/IMFePIrm28P.ttf",
+  "data/fonts/felltypes/IMFeFCrm28P.ttf",
+  "data/fonts/felltypes/IMFeGPit28P.ttf",
+  "data/fonts/felltypes/IMFeENit28P.ttf",
+  "data/fonts/felltypes/IMFeDPit28P.ttf",
+  "data/fonts/felltypes/IMFeENrm28P.ttf",
+  "data/fonts/felltypes/IMFeGPsc28P.ttf",
+  "data/fonts/felltypes/IMFePIsc28P.ttf",
+  "data/fonts/felltypes/IMFeFCsc28P.ttf",
+  "data/fonts/felltypes/IMFeFCit28P.ttf",
+  "data/fonts/bokor/Bokor.ttf",
+  "data/fonts/didactgothic/DidactGothic.ttf",
+  "data/fonts/allerta/Allerta-Medium.ttf",
+  "data/fonts/allerta/Allerta-Stencil.ttf",
+  "data/fonts/buda/Buda-Light.ttf",
+  "data/fonts/brawler/Brawler-Regular.ttf",
+  "data/fonts/carterone/CarterOne.ttf",
+  "data/fonts/candal/Candal.ttf",
+  "data/fonts/dorsa/Dorsa-Regular.ttf",
+  "data/fonts/crimson/CrimsonText-BoldItalic.ttf",
+  "data/fonts/crimson/CrimsonText-Bold.ttf",
+  "data/fonts/crimson/CrimsonText-Italic.ttf",
+  "data/fonts/crimson/CrimsonText-Roman.ttf",
+  "data/fonts/crimson/CrimsonText-Semibold.ttf",
+  "data/fonts/crimson/CrimsonText-SemiboldItalic.ttf",
+  "data/fonts/amaranth/Amaranth-Italic.ttf",
+  "data/fonts/amaranth/Amaranth-Bold.ttf",
+  "data/fonts/amaranth/Amaranth-Regular.ttf",
+  "data/fonts/amaranth/Amaranth-BoldItalic.ttf",
+  "data/fonts/crushed/Crushed.ttf",
+  "data/fonts/adamina/Adamina-Regular.ttf",
+  "data/fonts/aldrich/Aldrich-Regular.ttf",
+  "data/fonts/fanwoodtext/FanwoodText-Italic.ttf",
+  "data/fonts/fanwoodtext/FanwoodText-Regular.ttf",
+  "data/fonts/anonymouspro/AnonymousPro-Regular.ttf",
+  "data/fonts/anonymouspro/AnonymousPro-Bold.ttf",
+  "data/fonts/anonymouspro/AnonymousPro-Italic.ttf",
+  "data/fonts/anonymouspro/AnonymousPro-BoldItalic.ttf",
+  "data/fonts/bevan/Bevan.ttf",
+  "data/fonts/artifika/Artifika-Regular.ttf",
+  "data/fonts/anton/Anton.ttf",
+  "data/fonts/battambang/Battambang-Regular.ttf",
+  "data/fonts/battambang/Battambang-Bold.ttf",
+  "data/fonts/carme/Carme-Regular.ttf",
+  "data/fonts/cherrycreamsoda/CherryCreamSoda.ttf",
+  "data/fonts/deliusunicase/DeliusUnicase-Regular.ttf",
+  "data/fonts/comingsoon/ComingSoon.ttf",
+  "data/fonts/freehand/Freehand.ttf",
+  "data/fonts/alice/Alice-Regular.ttf",
+  "data/fonts/contrail/Contrail-Regular.ttf",
+  "data/fonts/cardo/Cardo-Bold.ttf",
+  "data/fonts/cardo/Cardo-Italic.ttf",
+  "data/fonts/cardo/Cardo-Regular.ttf",
+  "data/fonts/asset/Asset.ttf",
+  "data/fonts/changaone/ChangaOne-Regular.ttf",
+  "data/fonts/aclonica/Aclonica.ttf",
+  "data/fonts/craftygirls/CraftyGirls.ttf",
+  "data/fonts/architectsdaughter/ArchitectsDaughter.ttf",
+  "data/fonts/content/Content-Bold.ttf",
+  "data/fonts/content/Content-Regular.ttf",
+  "data/fonts/abel/Abel-Regular.ttf",
+  "data/fonts/cuprum/Cuprum.ttf",
+  "data/fonts/andika/Andika-R.ttf"
+};
+}  // namespace cmap_test_data
+}  // namespace sfntly
+
+#endif  // TYPOGRAPHY_FONT_SFNTLY_SRC_TEST_AUTOGENERATED_CMAP_TEST_DATA_H_
diff --git a/sfntly/cpp/src/test/bitmap_table_test.cc b/sfntly/cpp/src/test/bitmap_table_test.cc
new file mode 100644
index 0000000..df3ffc0
--- /dev/null
+++ b/sfntly/cpp/src/test/bitmap_table_test.cc
@@ -0,0 +1,209 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/port/file_input_stream.h"
+#include "sfntly/port/memory_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "sfntly/table/bitmap/ebdt_table.h"
+#include "sfntly/table/bitmap/eblc_table.h"
+#include "sfntly/table/bitmap/index_sub_table_format3.h"
+#include "sfntly/table/bitmap/index_sub_table_format4.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+
+namespace sfntly {
+
+const int32_t NUM_STRIKES = 4;
+const int32_t STRIKE1_ARRAY_OFFSET = 0xc8;
+const int32_t STRIKE1_INDEX_TABLE_SIZE = 0x4f4;
+const int32_t STRIKE1_NUM_INDEX_TABLES = 1;
+const int32_t STRIKE1_COLOR_REF = 0;
+const int32_t STRIKE1_START_GLYPH_INDEX = 0;
+const int32_t STRIKE1_END_GLYPH_INDEX = 623;
+const int32_t STRIKE1_PPEM_X = 10;
+const int32_t STRIKE1_PPEM_Y = 10;
+const int32_t STRIKE1_BIT_DEPTH = 1;
+const int32_t STRIKE1_FLAGS = 0x01;
+
+const int32_t STRIKE4_SUB1_INDEX_FORMAT = 3;
+const int32_t STRIKE4_SUB1_IMAGE_FORMAT = 1;
+const int32_t STRIKE4_SUB1_IMAGE_DATA_OFFSET = 0x00005893;
+const int32_t STRIKE4_SUB1_GLYPH_OFFSET[] = {
+    0x00005893, 0x00005898, 0x0000589d, 0x000058a2, 0x000058a7,
+    0x000058b2, 0x000058c2, 0x000058d0, 0x000058de, 0x000058e6 };
+const int32_t NUM_STRIKE4_SUB1_GLYPH_OFFSET = 10;
+const int32_t STRIKE4_SUB1_GLYPH2_LENGTH = 0x58a2 - 0x589d;
+
+bool CommonReadingTest(Font* raw_font) {
+  FontPtr font = raw_font;
+
+  EblcTablePtr bitmap_loca = down_cast<EblcTable*>(font->GetTable(Tag::EBLC));
+  EbdtTablePtr bitmap_table = down_cast<EbdtTable*>(font->GetTable(Tag::EBDT));
+
+  EXPECT_FALSE(bitmap_loca == NULL);
+  EXPECT_FALSE(bitmap_table == NULL);
+
+  EXPECT_EQ(bitmap_loca->NumSizes(), NUM_STRIKES);
+
+  // Strike 1
+  BitmapSizeTablePtr strike1 = bitmap_loca->GetBitmapSizeTable(0);
+  EXPECT_FALSE(strike1 == NULL);
+  EXPECT_EQ(strike1->IndexSubTableArrayOffset(), STRIKE1_ARRAY_OFFSET);
+  EXPECT_EQ(strike1->NumberOfIndexSubTables(), STRIKE1_NUM_INDEX_TABLES);
+  EXPECT_EQ(strike1->ColorRef(), STRIKE1_COLOR_REF);
+  EXPECT_EQ(strike1->StartGlyphIndex(), STRIKE1_START_GLYPH_INDEX);
+  EXPECT_EQ(strike1->EndGlyphIndex(), STRIKE1_END_GLYPH_INDEX);
+  EXPECT_EQ(strike1->PpemX(), STRIKE1_PPEM_X);
+  EXPECT_EQ(strike1->PpemY(), STRIKE1_PPEM_Y);
+  EXPECT_EQ(strike1->BitDepth(), STRIKE1_BIT_DEPTH);
+  EXPECT_EQ(strike1->FlagsAsInt(), STRIKE1_FLAGS);
+
+  // Strike 4
+  // In this test font, all strikes and all subtables have same glyphs.
+  BitmapSizeTablePtr strike4 = bitmap_loca->GetBitmapSizeTable(3);
+  EXPECT_FALSE(strike4 == NULL);
+  EXPECT_EQ(strike4->StartGlyphIndex(), STRIKE1_START_GLYPH_INDEX);
+  EXPECT_EQ(strike4->EndGlyphIndex(), STRIKE1_END_GLYPH_INDEX);
+  IndexSubTablePtr sub1 = strike4->GetIndexSubTable(0);
+  EXPECT_FALSE(sub1 == NULL);
+  EXPECT_EQ(sub1->image_format(), STRIKE4_SUB1_IMAGE_FORMAT);
+  EXPECT_EQ(sub1->first_glyph_index(), STRIKE1_START_GLYPH_INDEX);
+  EXPECT_EQ(sub1->last_glyph_index(), STRIKE1_END_GLYPH_INDEX);
+  EXPECT_EQ(sub1->image_data_offset(), STRIKE4_SUB1_IMAGE_DATA_OFFSET);
+
+  for (int32_t i = 0; i < NUM_STRIKE4_SUB1_GLYPH_OFFSET; ++i) {
+      EXPECT_EQ(sub1->GlyphOffset(i), STRIKE4_SUB1_GLYPH_OFFSET[i]);
+  }
+  return true;
+}
+
+bool TestReadingBitmapTable() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontArray font_array;
+  LoadFont(SAMPLE_BITMAP_FONT, factory, &font_array);
+  FontPtr font = font_array[0];
+  EXPECT_TRUE(CommonReadingTest(font));
+
+  EblcTablePtr bitmap_loca = down_cast<EblcTable*>(font->GetTable(Tag::EBLC));
+  BitmapSizeTablePtr strike1 = bitmap_loca->GetBitmapSizeTable(0);
+  BitmapSizeTablePtr strike4 = bitmap_loca->GetBitmapSizeTable(3);
+  IndexSubTablePtr sub1 = strike4->GetIndexSubTable(0);
+
+  EXPECT_EQ(strike1->IndexTableSize(), STRIKE1_INDEX_TABLE_SIZE);
+  EXPECT_EQ(sub1->index_format(), STRIKE4_SUB1_INDEX_FORMAT);
+
+  // Strike 4 Index Sub Table 1 is a Format 3
+  IndexSubTableFormat3Ptr sub3 =
+      down_cast<IndexSubTableFormat3*>(strike4->GetIndexSubTable(0));
+  EXPECT_FALSE(sub3 == NULL);
+  BitmapGlyphInfoPtr info;
+  info.Attach(sub3->GlyphInfo(2));
+  EXPECT_EQ(info->glyph_id(), 2);
+  EXPECT_EQ(info->block_offset(), STRIKE4_SUB1_IMAGE_DATA_OFFSET);
+  EXPECT_EQ(info->start_offset(),
+            STRIKE4_SUB1_GLYPH_OFFSET[2] - STRIKE4_SUB1_GLYPH_OFFSET[0]);
+  EXPECT_EQ(info->format(), STRIKE4_SUB1_IMAGE_FORMAT);
+  EXPECT_EQ(info->length(), STRIKE4_SUB1_GLYPH2_LENGTH);
+
+  return true;
+}
+
+// Function in subset_impl.cc
+extern
+void SubsetEBLC(EblcTable::Builder* eblc, const BitmapLocaList& new_loca);
+
+bool TestIndexFormatConversion() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray builder_array;
+  BuilderForFontFile(SAMPLE_BITMAP_FONT, factory, &builder_array);
+
+  FontBuilderPtr font_builder;
+  font_builder = builder_array[0];
+  EblcTableBuilderPtr eblc_builder =
+      down_cast<EblcTable::Builder*>(font_builder->GetTableBuilder(Tag::EBLC));
+  BitmapLocaList new_loca;
+  eblc_builder->GenerateLocaList(&new_loca);
+  SubsetEBLC(eblc_builder, new_loca);  // Format 3 -> 4
+
+  FontPtr new_font;
+  new_font.Attach(font_builder->Build());
+
+  // Serialize and reload the serialized font.
+  MemoryOutputStream os;
+  factory->SerializeFont(new_font, &os);
+
+#if defined (SFNTLY_DEBUG_BITMAP)
+  SerializeToFile(&os, "anon-mod.ttf");
+#endif
+
+  MemoryInputStream is;
+  is.Attach(os.Get(), os.Size());
+  FontArray font_array;
+  factory->LoadFonts(&is, &font_array);
+  new_font = font_array[0];
+
+  EXPECT_TRUE(CommonReadingTest(new_font));
+
+  // Strike 4 Index Sub Table 1 is a Format 4
+  EblcTablePtr bitmap_loca =
+      down_cast<EblcTable*>(new_font->GetTable(Tag::EBLC));
+  BitmapSizeTablePtr strike4 = bitmap_loca->GetBitmapSizeTable(3);
+  IndexSubTableFormat4Ptr sub4 =
+      down_cast<IndexSubTableFormat4*>(strike4->GetIndexSubTable(0));
+  EXPECT_FALSE(sub4 == NULL);
+
+  // And this subtable shall have exactly the same offset as original table
+  // since no subsetting happens.
+  FontArray original_font_array;
+  LoadFont(SAMPLE_BITMAP_FONT, factory, &original_font_array);
+  FontPtr font = original_font_array[0];
+  EXPECT_FALSE(font == NULL);
+  EblcTablePtr original_loca = down_cast<EblcTable*>(font->GetTable(Tag::EBLC));
+  EXPECT_FALSE(original_loca == NULL);
+  BitmapSizeTablePtr original_strike4 = bitmap_loca->GetBitmapSizeTable(3);
+  EXPECT_FALSE(original_strike4 == NULL);
+  IndexSubTableFormat3Ptr sub3 =
+      down_cast<IndexSubTableFormat3*>(strike4->GetIndexSubTable(0));
+  EXPECT_FALSE(sub3 == NULL);
+  EXPECT_EQ(strike4->StartGlyphIndex(), original_strike4->StartGlyphIndex());
+  EXPECT_EQ(strike4->EndGlyphIndex(), original_strike4->EndGlyphIndex());
+  for (int32_t i = strike4->StartGlyphIndex();
+               i <= strike4->EndGlyphIndex(); ++i) {
+    BitmapGlyphInfoPtr info, original_info;
+    info.Attach(sub4->GlyphInfo(i));
+    original_info.Attach(sub3->GlyphInfo(i));
+    EXPECT_EQ(info->format(), original_info->format());
+    EXPECT_EQ(info->glyph_id(), original_info->glyph_id());
+    EXPECT_EQ(info->length(), original_info->length());
+    EXPECT_EQ(info->offset(), original_info->offset());
+  }
+
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(BitmapTable, Reading) {
+  ASSERT_TRUE(sfntly::TestReadingBitmapTable());
+}
+
+TEST(BitmapTable, IndexFormatConversion) {
+  ASSERT_TRUE(sfntly::TestIndexFormatConversion());
+}
diff --git a/sfntly/cpp/src/test/byte_array_test.cc b/sfntly/cpp/src/test/byte_array_test.cc
new file mode 100644
index 0000000..40a6489
--- /dev/null
+++ b/sfntly/cpp/src/test/byte_array_test.cc
@@ -0,0 +1,146 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+
+#include "gtest/gtest.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/data/growable_memory_byte_array.h"
+
+namespace sfntly {
+namespace byte_array_test {
+
+const int32_t BYTE_ARRAY_SIZES[] =
+    {1, 7, 127, 128, 129, 255, 256, 257, 666, 1023, 10000, 0xffff, 0x10000};
+
+void FillTestByteArray(ByteArray* ba, int32_t size) {
+  for (int32_t i = 0; i < size; ++i) {
+    ba->Put(i, (byte_t)(i % 256));
+  }
+}
+
+void ReadByteArrayWithBuffer(ByteArray* ba, ByteVector* buffer, ByteVector* b) {
+  b->resize(ba->Length());
+  int32_t index = 0;
+  while (index < ba->Length()) {
+    int32_t bytes_read = ba->Get(index, buffer);
+    std::copy(buffer->begin(), buffer->begin() + bytes_read,
+              b->begin() + index);
+    index += bytes_read;
+  }
+}
+
+void ReadByteArrayWithSlidingWindow(ByteArray* ba, int window_size,
+                                    ByteVector* b) {
+  b->resize(ba->Length());
+  int32_t index = 0;
+  int32_t actual_window_size = window_size;
+  while (index < ba->Length()) {
+    actual_window_size =
+        std::min<int32_t>(actual_window_size, b->size() - index);
+    int32_t bytes_read = ba->Get(index, &((*b)[0]), index, actual_window_size);
+    index += bytes_read;
+  }
+}
+
+bool ReadComparison(ByteArray* ba1, ByteArray* ba2) {
+  // single byte reads
+  for (int i = 0; i < ba1->Length(); ++i) {
+    EXPECT_EQ(ba1->Get(i), ba2->Get(i));
+  }
+
+  ByteVector b1, b2;
+  // buffer reads
+  int increments = std::max<int32_t>(ba1->Length() / 11, 1);
+  for (int buffer_size = 1; buffer_size < ba1->Length();
+       buffer_size += increments) {
+    ByteVector buffer(buffer_size);
+    ReadByteArrayWithBuffer(ba1, &buffer, &b1);
+    ReadByteArrayWithBuffer(ba2, &buffer, &b2);
+    EXPECT_GT(b1.size(), static_cast<size_t>(0));
+    EXPECT_EQ(b1.size(), b2.size());
+    EXPECT_TRUE(std::equal(b1.begin(), b1.end(), b2.begin()));
+  }
+
+  // sliding window reads
+  b1.clear();
+  b2.clear();
+  for (int window_size = 1; window_size < ba1->Length();
+       window_size += increments) {
+    ReadByteArrayWithSlidingWindow(ba1, window_size, &b1);
+    ReadByteArrayWithSlidingWindow(ba2, window_size, &b2);
+    EXPECT_GT(b1.size(), static_cast<size_t>(0));
+    EXPECT_EQ(b1.size(), b2.size());
+    EXPECT_TRUE(std::equal(b1.begin(), b1.end(), b2.begin()));
+  }
+
+  return true;
+}
+
+bool CopyTest(ByteArray* ba) {
+  ByteArrayPtr fixed_copy = new MemoryByteArray(ba->Length());
+  ba->CopyTo(fixed_copy);
+  EXPECT_EQ(ba->Length(), fixed_copy->Length());
+  EXPECT_TRUE(ReadComparison(ba, fixed_copy));
+
+  ByteArrayPtr growable_copy = new GrowableMemoryByteArray();
+  ba->CopyTo(growable_copy);
+  EXPECT_EQ(ba->Length(), growable_copy->Length());
+  EXPECT_TRUE(ReadComparison(ba, growable_copy));
+
+  return true;
+}
+
+bool ByteArrayTester(ByteArray* ba) {
+  return CopyTest(ba);
+}
+
+}  // namespace byte_array_test
+
+bool TestMemoryByteArray() {
+  fprintf(stderr, "fixed mem: size ");
+  for (size_t i = 0;
+       i < sizeof(byte_array_test::BYTE_ARRAY_SIZES) / sizeof(int32_t); ++i) {
+    int32_t size = byte_array_test::BYTE_ARRAY_SIZES[i];
+    fprintf(stderr, "%d ", size);
+    ByteArrayPtr ba = new MemoryByteArray(size);
+    byte_array_test::FillTestByteArray(ba, size);
+    EXPECT_TRUE(byte_array_test::ByteArrayTester(ba));
+  }
+  fprintf(stderr, "\n");
+  return true;
+}
+
+bool TestGrowableMemoryByteArray() {
+  fprintf(stderr, "growable mem: size ");
+  for (size_t i = 0;
+       i < sizeof(byte_array_test::BYTE_ARRAY_SIZES) / sizeof(int32_t); ++i) {
+    int32_t size = byte_array_test::BYTE_ARRAY_SIZES[i];
+    fprintf(stderr, "%d ", size);
+    ByteArrayPtr ba = new GrowableMemoryByteArray();
+    byte_array_test::FillTestByteArray(ba, size);
+    EXPECT_TRUE(byte_array_test::ByteArrayTester(ba));
+  }
+  fprintf(stderr, "\n");
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(ByteArray, All) {
+  ASSERT_TRUE(sfntly::TestMemoryByteArray());
+  ASSERT_TRUE(sfntly::TestGrowableMemoryByteArray());
+}
diff --git a/sfntly/cpp/src/test/chrome_subsetter.cc b/sfntly/cpp/src/test/chrome_subsetter.cc
new file mode 100644
index 0000000..9563ab1
--- /dev/null
+++ b/sfntly/cpp/src/test/chrome_subsetter.cc
@@ -0,0 +1,75 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sample/chromium/font_subsetter.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+
+namespace {
+  // Use an additional variable to easily change name for testing.
+  const char* kInputFileName = sfntly::SAMPLE_TTF_FILE;
+  const char* kFontName = "Tuffy";
+  const char* kOutputFileName = "tuffy-s.ttf";
+  // The subset we want: Hello, world!
+  // The array is unsorted to verify that the subsetter gets the glyph id
+  // correctly.
+  const unsigned int kGlyphIds[] = { 43, 72, 79, 82, 15, 3, 90, 85, 71, 4 };
+  const unsigned int kGlyphIdsCount = sizeof(kGlyphIds) / sizeof(unsigned int);
+}
+
+// This function is deliberately located at global namespace.
+bool TestChromeSubsetter() {
+  sfntly::ByteVector input_buffer;
+  sfntly::LoadFile(kInputFileName, &input_buffer);
+  EXPECT_GT(input_buffer.size(), (size_t)0);
+
+  unsigned char* output_buffer = NULL;
+  int output_length =
+      SfntlyWrapper::SubsetFont(kFontName,
+                                &(input_buffer[0]),
+                                input_buffer.size(),
+                                kGlyphIds,
+                                kGlyphIdsCount,
+                                &output_buffer);
+
+  EXPECT_GT(output_length, 0);
+
+  if (output_length > 0) {
+    FILE* output_file = NULL;
+#if defined WIN32
+    fopen_s(&output_file, kOutputFileName, "wb");
+#else
+    output_file = fopen(kOutputFileName, "wb");
+#endif
+    EXPECT_TRUE((output_file != NULL));
+    if (output_file) {
+      int byte_count = fwrite(output_buffer, 1, output_length, output_file);
+      EXPECT_EQ(byte_count, output_length);
+      fflush(output_file);
+      fclose(output_file);
+    }
+
+    delete[] output_buffer;
+    return true;
+  }
+
+  return false;
+}
+
+TEST(ChromeSubsetter, All) {
+  EXPECT_TRUE(TestChromeSubsetter());
+}
diff --git a/sfntly/cpp/src/test/cmap_editing_test.cc b/sfntly/cpp/src/test/cmap_editing_test.cc
new file mode 100644
index 0000000..6df2720
--- /dev/null
+++ b/sfntly/cpp/src/test/cmap_editing_test.cc
@@ -0,0 +1,101 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <map>
+#include <algorithm>
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/font_header_table.h"
+#include "sfntly/tag.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/port/endian.h"
+#include "sfntly/port/file_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/port/refcount.h"
+#include "gtest/gtest.h"
+
+namespace sfntly {
+TEST(CMapEditingTest, RemoveAllButOneCMap) {
+  FontBuilderArray builders;
+  FontFactoryPtr font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  BuilderForFontFile(SAMPLE_TTF_FILE, font_factory, &builders);
+  ASSERT_FALSE(builders.empty());
+  FontBuilderPtr font_builder = builders[0];
+  Ptr<CMapTable::Builder> cmap_table_builder =
+      (CMapTable::Builder*)font_builder->GetTableBuilder(Tag::cmap);
+  ASSERT_NE(cmap_table_builder, reinterpret_cast<CMapTable::Builder*>(NULL));
+  CMapTable::CMapBuilderMap*
+      cmap_builders = cmap_table_builder->GetCMapBuilders();
+  ASSERT_FALSE(cmap_builders->empty());
+
+  for (CMapTable::CMapBuilderMap::iterator
+           it = cmap_builders->begin(); it != cmap_builders->end();) {
+    if (it->second->cmap_id() == CMapTable::WINDOWS_BMP) {
+      ++it;
+    } else {
+      cmap_builders->erase(it++);
+    }
+  }
+  ASSERT_EQ(cmap_builders->size(), (uint32_t)1);
+  Font* font = font_builder->Build();
+  CMapTablePtr cmap_table = down_cast<CMapTable*>(font->GetTable(Tag::cmap));
+  ASSERT_EQ(1, cmap_table->NumCMaps());
+  CMapTable::CMapPtr cmap;
+  cmap.Attach(cmap_table->GetCMap(CMapTable::WINDOWS_BMP));
+  ASSERT_EQ(CMapTable::WINDOWS_BMP, cmap->cmap_id());
+  delete font;
+}
+
+TEST(CMapEditingTest, CopyAllCMapsToNewFont) {
+  FontArray fonts;
+  FontFactoryPtr font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  LoadFont(SAMPLE_TTF_FILE, font_factory, &fonts);
+
+  ASSERT_FALSE(fonts.empty());
+  ASSERT_FALSE(fonts[0] == NULL);
+  FontPtr font = fonts[0];
+  CMapTablePtr cmap_table = down_cast<CMapTable*>(font->GetTable(Tag::cmap));
+  FontBuilderPtr font_builder;
+  font_builder.Attach(font_factory->NewFontBuilder());
+  Ptr<CMapTable::Builder> cmap_table_builder =
+      (CMapTable::Builder*)font_builder->NewTableBuilder(Tag::cmap);
+
+  CMapTable::CMapIterator cmap_iter(cmap_table, NULL);
+  while (cmap_iter.HasNext()) {
+    CMapTable::CMapPtr cmap;
+    cmap.Attach(cmap_iter.Next());
+    if (!cmap)
+      continue;
+    cmap_table_builder->NewCMapBuilder(cmap->cmap_id(), cmap->ReadFontData());
+  }
+
+  FontPtr new_font;
+  new_font.Attach(font_builder->Build());
+  CMapTablePtr new_cmap_table =
+      down_cast<CMapTable*>(font->GetTable(Tag::cmap));
+  ASSERT_EQ(cmap_table->NumCMaps(), new_cmap_table->NumCMaps());
+  CMapTable::CMapPtr cmap;
+  cmap.Attach(cmap_table->GetCMap(CMapTable::WINDOWS_BMP));
+  ASSERT_NE(cmap, reinterpret_cast<CMapTable::CMap*>(NULL));
+  ASSERT_EQ(CMapTable::WINDOWS_BMP, cmap->cmap_id());
+}
+}
diff --git a/sfntly/cpp/src/test/cmap_iterator_test.cc b/sfntly/cpp/src/test/cmap_iterator_test.cc
new file mode 100644
index 0000000..2e8e6fe
--- /dev/null
+++ b/sfntly/cpp/src/test/cmap_iterator_test.cc
@@ -0,0 +1,156 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <string.h>
+
+#include <vector>
+#include <string>
+#include <algorithm>
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/tag.h"
+#include "sfntly/port/type.h"
+#include "sfntly/port/refcount.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+
+#include "gtest/gtest.h"
+
+#if GTEST_HAS_PARAM_TEST
+
+namespace sfntly {
+using ::testing::TestWithParam;
+using ::testing::Values;
+
+typedef std::vector<bool> BitSet;
+
+class CMapIteratorTestCase {
+ public:
+  CMapIteratorTestCase(int32_t platform_id, int32_t encoding_id,
+                       const char* file_name)
+      : platform_id_(platform_id),
+        encoding_id_(encoding_id),
+        file_name_(file_name) {
+  }
+  ~CMapIteratorTestCase() {}
+  int32_t platform_id() const { return platform_id_; }
+  int32_t encoding_id() const { return encoding_id_; }
+  const char* file_name() const { return file_name_; }
+
+ private:
+  int32_t platform_id_;
+  int32_t encoding_id_;
+  const char* file_name_;
+};
+
+class CMapIteratorTests
+    : public ::testing::TestWithParam<CMapIteratorTestCase> {
+ public:
+  virtual void SetUp();
+  virtual void TearDown() {}
+
+  BitSet* GenerateCMapEntries(int32_t start, int32_t count);
+  int32_t CompareCMapIterAndBitSet(CMapTable::CMap::CharacterIterator*
+                                   character_iterator,
+                                   BitSet* bit_set);
+
+  Ptr<CMapTable::CMap> cmap_;
+};
+
+void CMapIteratorTests::SetUp() {
+  FontArray fonts;
+  Ptr<FontFactory> font_factory;
+  const char* file_name = GetParam().file_name();
+  LoadFont(file_name, font_factory, &fonts);
+  Ptr<Font> font;
+  font.Attach(fonts[0].Detach());
+  Ptr<CMapTable> cmap_table = down_cast<CMapTable*>(font->GetTable(Tag::cmap));
+  ASSERT_FALSE(cmap_table == NULL);
+  cmap_.Attach(cmap_table->GetCMap(GetParam().platform_id(),
+                                   GetParam().encoding_id()));
+  ASSERT_FALSE(cmap_ == NULL);
+}
+
+BitSet* CMapIteratorTests::GenerateCMapEntries(int32_t start, int32_t count) {
+  BitSet* entries = new BitSet(count);
+  for (int32_t c = start; c < start + count; ++c) {
+    int32_t g = cmap_->GlyphId(c);
+    if (g != CMapTable::NOTDEF)
+      (*entries)[c] = true;
+  }
+  return entries;
+}
+
+int32_t
+CMapIteratorTests::
+CompareCMapIterAndBitSet(CMapTable::CMap::CharacterIterator* character_iterator,
+                         BitSet* bit_set) {
+  int32_t iterator_not_bitset_count = 0;
+  BitSet::iterator end = bit_set->end(),
+      beginning = bit_set->begin(),
+      init_beginning = beginning,
+      current = std::find(beginning, end, true);
+  for (int32_t next_bit = current - beginning;
+       character_iterator->HasNext() && current != end;
+       next_bit = current - init_beginning) {
+    int32_t c = character_iterator->Next();
+    EXPECT_TRUE(c <= next_bit || current == end);
+    if (!(c <= next_bit || current == end))
+      return -1;
+    if (c == next_bit) {
+      beginning = current + 1;
+      current = std::find(beginning, end, true);
+    } else {
+      iterator_not_bitset_count++;
+    }
+  }
+  EXPECT_EQ(end, current);
+#if defined (SFNTLY_DEBUG_CMAP)
+  fprintf(stderr, "%s %d: Differences between iterator and bitset: %d\n",
+          cmap_->format(), GetParam().file_name(), iterator_not_bitset_count);
+#endif
+  return iterator_not_bitset_count;
+}
+
+TEST_P(CMapIteratorTests, IteratorTest) {
+  BitSet* bit_set = GenerateCMapEntries(0, 0x10ffff);
+  CMapTable::CMap::CharacterIterator* character_iterator = NULL;
+  character_iterator = cmap_->Iterator();
+  EXPECT_NE(character_iterator,
+            reinterpret_cast<CMapTable::CMap::CharacterIterator*>(NULL));
+  CompareCMapIterAndBitSet(character_iterator, bit_set);
+  delete character_iterator;
+  delete bit_set;
+}
+
+CMapIteratorTestCase kCMapIteratorTestsTestCases[] = {
+  CMapIteratorTestCase(CMapTable::WINDOWS_BMP.platform_id,
+                       CMapTable::WINDOWS_BMP.encoding_id,
+                       SAMPLE_TTF_FILE)
+};
+
+INSTANTIATE_TEST_CASE_P(CMapIteratorTests,
+                        CMapIteratorTests,
+                        ::testing::ValuesIn(kCMapIteratorTestsTestCases));
+}
+
+#else
+
+TEST(DummyTest, ValueParameterizedTestsAreNotSupportedOnThisPlatform) {}
+
+#endif  // GTEST_HAS_PARAM
diff --git a/sfntly/cpp/src/test/cmap_test.cc b/sfntly/cpp/src/test/cmap_test.cc
new file mode 100644
index 0000000..02bf8a2
--- /dev/null
+++ b/sfntly/cpp/src/test/cmap_test.cc
@@ -0,0 +1,213 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/port/type.h"
+#include <assert.h>
+#include <unicode/ucnv.h>
+
+#include <string>
+#include <iostream>
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/cmap_table.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/table/core/font_header_table.h"
+#include "sfntly/tag.h"
+
+#include "test/test_utils.h"
+#include "test/test_font_utils.h"
+#include "test/test_data.h"
+
+#if GTEST_HAS_PARAM_TEST
+
+namespace sfntly {
+using ::testing::TestWithParam;
+using ::testing::Values;
+
+class CMapTestCase {
+ public:
+  CMapTestCase(const char* font_name,
+               int32_t first_platform_id,
+               int32_t first_encoding_id,
+               const char* first_charset_name,
+               int32_t second_platform_id,
+               int32_t second_encoding_id,
+               const char* second_charset_name,
+               int32_t low_char,
+               int32_t high_char)
+      : font_name_(font_name),
+        first_platform_id_(first_platform_id),
+        first_encoding_id_(first_encoding_id),
+        first_charset_name_(first_charset_name),
+        second_platform_id_(second_platform_id),
+        second_encoding_id_(second_encoding_id),
+        second_charset_name_(second_charset_name),
+        low_char_(low_char),
+        high_char_(high_char) {
+  }
+
+  const char* font_name() const { return font_name_; }
+  int32_t first_platform_id() const { return first_platform_id_; }
+  int32_t first_encoding_id() const { return first_encoding_id_; }
+  const char* first_charset_name() const { return first_charset_name_; }
+  int32_t second_platform_id() const { return second_platform_id_; }
+  int32_t second_encoding_id() const { return second_encoding_id_; }
+  const char* second_charset_name() const { return second_charset_name_; }
+  int32_t low_char() const { return low_char_; }
+  int32_t high_char() const { return high_char_; }
+
+ private:
+  const char* font_name_;
+  int32_t first_platform_id_;
+  int32_t first_encoding_id_;
+  const char* first_charset_name_;
+  int32_t second_platform_id_;
+  int32_t second_encoding_id_;
+  const char* second_charset_name_;
+  int32_t low_char_;
+  int32_t high_char_;
+};
+
+class CMapTests : public :: testing::TestWithParam<CMapTestCase> {
+ public:
+  CMapTests() : encoder1_(NULL), encoder2_(NULL), successful_setup_(false) {
+  }
+  virtual void SetUp() {}
+  virtual void TearDown();
+
+  void CommonSetUp(FontArray* font_array);
+
+  void CompareCMaps();
+
+  Ptr<CMapTable::CMap> cmap1_;
+  Ptr<CMapTable::CMap> cmap2_;
+  UConverter* encoder1_;
+  UConverter* encoder2_;
+  bool successful_setup_;
+};
+
+::std::ostream& operator<<(::std::ostream& os, const CMapTestCase *test_case) {
+  return os << "("
+            << test_case->font_name() << ", "
+            << test_case->first_platform_id() << ", "
+            << test_case->first_encoding_id() << ", "
+            << test_case->first_charset_name() << ", "
+            << test_case->second_platform_id() << ", "
+            << test_case->second_encoding_id() << ", "
+            << test_case->second_charset_name() << ", "
+            << test_case->low_char() << ", "
+            << test_case->high_char() << ")";
+}
+
+void CMapTests::CommonSetUp(FontArray* font_array) {
+  ASSERT_NE(font_array, reinterpret_cast<FontArray*>(NULL));
+  ASSERT_FALSE(font_array->empty());
+  Ptr<Font> font;
+  font = font_array->at(0);
+  ASSERT_NE(font, reinterpret_cast<Font*>(NULL));
+  Ptr<CMapTable> cmap_table =
+      down_cast<CMapTable*>(font->GetTable(Tag::cmap));
+  cmap1_.Attach(cmap_table->GetCMap(GetParam().first_platform_id(),
+                                    GetParam().first_encoding_id()));
+  ASSERT_NE((cmap1_), reinterpret_cast<CMapTable::CMap*>(NULL));
+  cmap2_.Attach(cmap_table->GetCMap(GetParam().second_platform_id(),
+                                    GetParam().second_encoding_id()));
+  ASSERT_NE((cmap2_), reinterpret_cast<CMapTable::CMap*>(NULL));
+  encoder1_ = TestUtils::GetEncoder(GetParam().first_charset_name());
+  encoder2_ = TestUtils::GetEncoder(GetParam().second_charset_name());
+  successful_setup_ = true;
+}
+
+void CMapTests::TearDown() {
+  if (encoder1_)
+    ucnv_close(encoder1_);
+  if (encoder2_)
+    ucnv_close(encoder2_);
+}
+
+void CMapTests::CompareCMaps() {
+  ASSERT_TRUE(successful_setup_);
+  for (int32_t uchar = GetParam().low_char();
+       uchar <= GetParam().high_char(); ++uchar) {
+    int32_t c1 = uchar;
+    if (encoder1_ != NULL)
+      c1 = TestUtils::EncodeOneChar(encoder1_, (int16_t)uchar);
+    int32_t c2 = uchar;
+    if (encoder2_ != NULL)
+      c2 = TestUtils::EncodeOneChar(encoder2_, (int16_t)uchar);
+    int32_t glyph_id1 = cmap1_->GlyphId(c1);
+    int32_t glyph_id2 = cmap2_->GlyphId(c2);
+#ifdef SFNTLY_DEBUG_CMAP
+    if (glyph_id1 != glyph_id2)
+      fprintf(stderr, "%x: g1=%x, %x: g2=%x\n", c1, glyph_id1, c2, glyph_id2);
+#endif
+    ASSERT_EQ(glyph_id1, glyph_id2);
+  }
+#ifdef SFNTLY_SFNTLY_DEBUG_CMAPCMAP
+  fprintf(stderr, "\n");
+#endif
+}
+
+TEST_P(CMapTests, GlyphsBetweenCMapsFingerprint) {
+  Ptr<FontFactory> font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  font_factory->FingerprintFont(true);
+  FontArray font_array;
+  LoadFont(GetParam().font_name(), font_factory, &font_array);
+  CommonSetUp(&font_array);
+  CompareCMaps();
+}
+
+TEST_P(CMapTests, GlyphsBetweenCMapsNoFingerprint) {
+  Ptr<FontFactory> font_factory;
+  font_factory.Attach(FontFactory::GetInstance());
+  FontArray font_array;
+  LoadFont(GetParam().font_name(), font_factory, &font_array);
+  CommonSetUp(&font_array);
+  CompareCMaps();
+}
+
+TEST_P(CMapTests, GlyphsBetweenCMapsUsingByteVector) {
+  FontArray font_array;
+  LoadFontUsingByteVector(GetParam().font_name(), true, &font_array);
+  CommonSetUp(&font_array);
+  CompareCMaps();
+}
+
+CMapTestCase kCMapTestsTestCases[] = {
+  CMapTestCase(SAMPLE_TTF_FILE,
+               PlatformId::kWindows,
+               WindowsEncodingId::kUnicodeUCS2,
+               NULL,
+               PlatformId::kUnicode,
+               UnicodeEncodingId::kUnicode2_0_BMP,
+               NULL,
+               (int32_t)0x20,
+               (int32_t)0x7f),
+};
+
+INSTANTIATE_TEST_CASE_P(CMapTests,
+                        CMapTests,
+                        ::testing::ValuesIn(kCMapTestsTestCases));
+}
+
+#else
+
+TEST(DummyTest, ValueParameterizedTestsAreNotSupportedOnThisPlatform) {}
+
+#endif  // GTEST_HAS_PARAM
diff --git a/sfntly/cpp/src/test/endian_test.cc b/sfntly/cpp/src/test/endian_test.cc
new file mode 100644
index 0000000..0d9da09
--- /dev/null
+++ b/sfntly/cpp/src/test/endian_test.cc
@@ -0,0 +1,77 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/tag.h"
+#include "sfntly/data/growable_memory_byte_array.h"
+#include "sfntly/data/writable_font_data.h"
+#include "sfntly/math/fixed1616.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "sfntly/data/font_output_stream.h"
+
+namespace sfntly {
+
+bool TestEndian() {
+  byte_t test_data[] = {
+      0x68, 0x65, 0x61, 0x64,  // 0: head
+      0xca, 0xca, 0xca, 0xca,  // 4: ubyte, byte, char
+      0x00, 0x18, 0x80, 0x18,  // 8: ushort, short
+      0x00, 0x00, 0x18, 0x00,  // 12: uint24
+      0x00, 0x00, 0x00, 0x18,  // 16: ulong
+      0xff, 0xff, 0xff, 0x00,  // 20: long
+      0x00, 0x01, 0x00, 0x00   // 24: fixed
+  };
+
+  ByteArrayPtr ba1 = new GrowableMemoryByteArray();
+  for (size_t i = 0; i < sizeof(test_data); ++i) {
+    ba1->Put(i, test_data[i]);
+  }
+  ReadableFontDataPtr rfd = new ReadableFontData(ba1);
+  EXPECT_EQ(rfd->ReadULongAsInt(0), Tag::head);
+  EXPECT_EQ(rfd->ReadUByte(4), 202);
+  EXPECT_EQ(rfd->ReadByte(5), -54);
+  EXPECT_EQ(rfd->ReadChar(6), 202);
+  EXPECT_EQ(rfd->ReadUShort(8), 24);
+  EXPECT_EQ(rfd->ReadShort(10), -32744);
+  EXPECT_EQ(rfd->ReadUInt24(12), 24);
+  EXPECT_EQ(rfd->ReadULong(16), 24);
+  EXPECT_EQ(rfd->ReadLong(20), -256);
+  EXPECT_EQ(rfd->ReadFixed(24), Fixed1616::Fixed(1, 0));
+
+  MemoryOutputStream os;
+  FontOutputStream fos(&os);
+  fos.WriteULong(Tag::head);
+  fos.Write(202);
+  fos.Write(202);
+  fos.Write(202);
+  fos.Write(202);
+  fos.WriteUShort(24);
+  fos.WriteShort(-32744);
+  fos.WriteUInt24(24);
+  fos.WriteChar(0);
+  fos.WriteULong(24);
+  fos.WriteLong(-256);
+  fos.WriteFixed(Fixed1616::Fixed(1, 0));
+  EXPECT_EQ(memcmp(os.Get(), test_data, sizeof(test_data)), 0);
+
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(Endian, All) {
+  ASSERT_TRUE(sfntly::TestEndian());
+}
diff --git a/sfntly/cpp/src/test/file_io_test.cc b/sfntly/cpp/src/test/file_io_test.cc
new file mode 100644
index 0000000..3cec4d6
--- /dev/null
+++ b/sfntly/cpp/src/test/file_io_test.cc
@@ -0,0 +1,153 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+
+#include "gtest/gtest.h"
+#include "sfntly/port/file_input_stream.h"
+#include "sfntly/data/font_input_stream.h"
+#include "test/test_data.h"
+
+namespace sfntly {
+
+bool TestFileInputStream() {
+  FILE* file_handle = NULL;
+#if defined (WIN32)
+  fopen_s(&file_handle, SAMPLE_TTF_FILE, "rb");
+#else
+  file_handle = fopen(SAMPLE_TTF_FILE, "rb");
+#endif
+  if (file_handle == NULL) {
+    return false;
+  }
+  fseek(file_handle, 0, SEEK_END);
+  size_t length = ftell(file_handle);
+  fseek(file_handle, 0, SEEK_SET);
+  ByteVector b1;
+  b1.resize(length);
+  size_t bytes_read = fread(&(b1[0]), 1, length, file_handle);
+  EXPECT_EQ(bytes_read, length);
+  fclose(file_handle);
+
+  // Full file reading test
+  FileInputStream is;
+  is.Open(SAMPLE_TTF_FILE);
+  EXPECT_EQ(length, (size_t)is.Available());
+  ByteVector b2;
+  is.Read(&b2, 0, length);
+  is.Close();
+  EXPECT_EQ(memcmp(&(b1[0]), &(b2[0]), length), 0);
+  b2.clear();
+
+  // Partial reading test
+  is.Open(SAMPLE_TTF_FILE);
+  is.Skip(89);
+  is.Read(&b2, 0, 100);
+  EXPECT_EQ(memcmp(&(b1[89]), &(b2[0]), 100), 0);
+  b2.clear();
+
+  // Skip test
+  is.Skip(-89);
+  is.Read(&b2, 0, 100);
+  EXPECT_EQ(memcmp(&(b1[100]), &(b2[0]), 100), 0);
+  b2.clear();
+  is.Skip(100);
+  is.Read(&b2, 0, 100);
+  EXPECT_EQ(memcmp(&(b1[300]), &(b2[0]), 100), 0);
+  is.Skip(-400);
+  b2.clear();
+
+  // Offset test
+  is.Read(&b2, 0, 100);
+  is.Read(&b2, 100, 100);
+  EXPECT_EQ(memcmp(&(b1[0]), &(b2[0]), 200), 0);
+
+  // Unread test
+  ByteVector b3;
+  b3.resize(200);
+  is.Unread(&b3);
+  EXPECT_EQ(memcmp(&(b3[0]), &(b2[0]), 200), 0);
+
+  return true;
+}
+
+bool TestFontInputStreamBasic() {
+  FILE* file_handle = NULL;
+#if defined (WIN32)
+  fopen_s(&file_handle, SAMPLE_TTF_FILE, "rb");
+#else
+  file_handle = fopen(SAMPLE_TTF_FILE, "rb");
+#endif
+  if (file_handle == NULL) {
+    return false;
+  }
+  fseek(file_handle, 0, SEEK_END);
+  size_t length = ftell(file_handle);
+  fseek(file_handle, 0, SEEK_SET);
+  ByteVector b1;
+  b1.resize(length);
+  size_t bytes_read = fread(&(b1[0]), 1, length, file_handle);
+  EXPECT_EQ(bytes_read, length);
+  fclose(file_handle);
+
+  FileInputStream is;
+  is.Open(SAMPLE_TTF_FILE);
+  FontInputStream font_is1(&is);
+  EXPECT_EQ((size_t)font_is1.Available(), length);
+
+  ByteVector b2;
+  font_is1.Read(&b2, 0, length);
+  font_is1.Close();
+  EXPECT_EQ(memcmp(&(b1[0]), &(b2[0]), length), 0);
+  b2.clear();
+
+  is.Open(SAMPLE_TTF_FILE);
+  is.Skip(89);
+  FontInputStream font_is2(&is, 200);
+  font_is2.Read(&b2, 0, 100);
+  EXPECT_EQ(memcmp(&(b1[89]), &(b2[0]), 100), 0);
+  font_is2.Read(&b2, 100, 100);
+  EXPECT_EQ(memcmp(&(b1[89]), &(b2[0]), 200), 0);
+  b2.clear();
+  font_is2.Skip(-200);
+  font_is2.Read(&b2, 0, 100);
+  EXPECT_EQ(memcmp(&(b1[89]), &(b2[0]), 100), 0);
+
+  return true;
+}
+
+bool TestFontInputStreamTableLoading() {
+  FileInputStream is;
+  is.Open(SAMPLE_TTF_FILE);
+  FontInputStream font_is(&is);
+
+  font_is.Skip(TTF_OFFSET[SAMPLE_TTF_FEAT]);
+  FontInputStream gdef_is(&font_is, TTF_LENGTH[SAMPLE_TTF_FEAT]);
+  ByteVector feat_data;
+  gdef_is.Read(&feat_data, 0, TTF_LENGTH[SAMPLE_TTF_FEAT]);
+  EXPECT_EQ(memcmp(&(feat_data[0]), TTF_FEAT_DATA,
+                   TTF_LENGTH[SAMPLE_TTF_FEAT]), 0);
+
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(FileIO, All) {
+  ASSERT_TRUE(sfntly::TestFileInputStream());
+  ASSERT_TRUE(sfntly::TestFontInputStreamBasic());
+  ASSERT_TRUE(sfntly::TestFontInputStreamTableLoading());
+}
diff --git a/sfntly/cpp/src/test/font_data_test.cc b/sfntly/cpp/src/test/font_data_test.cc
new file mode 100644
index 0000000..4b0db64
--- /dev/null
+++ b/sfntly/cpp/src/test/font_data_test.cc
@@ -0,0 +1,337 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <vector>
+#include <algorithm>
+
+#include "gtest/gtest.h"
+#include "sfntly/port/type.h"
+#include "sfntly/data/writable_font_data.h"
+#include "sfntly/data/memory_byte_array.h"
+
+namespace sfntly {
+
+const int32_t BYTE_ARRAY_SIZES[] =
+  {1, 7, 127, 128, 129, 255, 256, 257, 666, 1023, 0x10000};
+
+// array data for searching
+const int32_t LOWER_BYTE_ARRAY_FOR_SEARCHING[] = {2, 4, 7, 13, 127};
+const int32_t UPPER_BYTE_ARRAY_FOR_SEARCHING[] = {2, 5, 12, 16, 256};
+const int32_t kLowerByteArrayForSearchingLength = 5;
+const int32_t kUpperByteArrayForSearchingLength = 5;
+
+// search test result pairs - number to search for; index found at
+const int32_t SEARCH_TEST_PAIRS[][2] = {
+  {0, -1}, {1, -1}, {2, 0}, {3, -1}, {4, 1}, {5, 1}, {6, -1}, {12, 2},
+  {13, 3}, {17, -1}, {126, -1}, {127, 4}, {256, 4}, {257, -1}, {0x1000, -1}
+};
+const int32_t kSearchTestPairsLength = 15;
+
+// offset and start index data for searching data
+// array data size, lower_start_index, lower_offset, upper_start_index,
+// upper_offset
+const int32_t SEARCH_TEST_OFFSETS[][5] = {
+  // lower[], upper[]
+  { (kLowerByteArrayForSearchingLength + kUpperByteArrayForSearchingLength)
+    * DataSize::kUSHORT,
+    0,
+    DataSize::kUSHORT,
+    kLowerByteArrayForSearchingLength * DataSize::kUSHORT,
+    DataSize::kUSHORT },
+
+  // {lower, upper} []
+  { (kLowerByteArrayForSearchingLength + kUpperByteArrayForSearchingLength)
+    * DataSize::kUSHORT,
+    0,
+    2 * DataSize::kUSHORT,
+    DataSize::kUSHORT,
+    2 * DataSize::kUSHORT },
+
+  // upper[], lower[]
+  { (kLowerByteArrayForSearchingLength + kUpperByteArrayForSearchingLength)
+    * DataSize::kUSHORT,
+    kLowerByteArrayForSearchingLength * DataSize::kUSHORT,
+    DataSize::kUSHORT,
+    0,
+    DataSize::kUSHORT },
+
+  // {upper, lower} []
+  { (kLowerByteArrayForSearchingLength + kUpperByteArrayForSearchingLength)
+    * DataSize::kUSHORT,
+    DataSize::kUSHORT,
+    2 * DataSize::kUSHORT,
+    0,
+    2 * DataSize::kUSHORT }
+};
+const int32_t kSearchTestOffsetLength = 4;
+
+ReadableFontData*
+FillTestFontDataWithShortsForSearching(WritableFontData* wfd,
+                                       const int32_t* lower_data,
+                                       int32_t lower_start_index,
+                                       int32_t lower_offset,
+                                       const int32_t* upper_data,
+                                       int32_t upper_start_index,
+                                       int32_t upper_offset) {
+  // lower data
+  int offset = lower_start_index;
+  for (int32_t i = 0; i < kLowerByteArrayForSearchingLength; ++i) {
+    wfd->WriteUShort(offset, lower_data[i]);
+    offset += lower_offset;
+  }
+
+  // upper data
+  offset = upper_start_index;
+  for (int32_t i = 0; i < kUpperByteArrayForSearchingLength; ++i) {
+    wfd->WriteUShort(offset, upper_data[i]);
+    offset += upper_offset;
+  }
+
+  return wfd;
+}
+
+bool TestReadableFontDataSearching() {
+  for (int32_t i = 0; i < kSearchTestOffsetLength; ++i) {
+    const int32_t* array_setup_offset = SEARCH_TEST_OFFSETS[i];
+    WritableFontDataPtr wfd;
+    wfd.Attach(WritableFontData::CreateWritableFontData(array_setup_offset[0]));
+    FillTestFontDataWithShortsForSearching(wfd,
+                                           LOWER_BYTE_ARRAY_FOR_SEARCHING,
+                                           array_setup_offset[1],
+                                           array_setup_offset[2],
+                                           UPPER_BYTE_ARRAY_FOR_SEARCHING,
+                                           array_setup_offset[3],
+                                           array_setup_offset[4]);
+    for (int32_t j = 0; j < kSearchTestPairsLength; ++j) {
+      const int32_t* test_case = SEARCH_TEST_PAIRS[j];
+      int32_t found = wfd->SearchUShort(array_setup_offset[1],
+                                        array_setup_offset[2],
+                                        array_setup_offset[3],
+                                        array_setup_offset[4],
+                                        kLowerByteArrayForSearchingLength,
+                                        test_case[0]);
+#if defined (SFNTLY_DEBUG_FONTDATA)
+      fprintf(stderr, "Searching for %d; Got %d; Expected %d; "
+              "[test %d][offset %d]\n",
+              test_case[0], found, test_case[1], j, i);
+#endif
+      EXPECT_EQ(test_case[1], found);
+    }
+  }
+  return true;
+}
+
+void FillTestByteArray(ByteArray* ba, int32_t size) {
+  for (int32_t i = 0; i < size; ++i) {
+    ba->Put(i, (byte_t)(i % 256));
+  }
+}
+
+void ReadFontDataWithSingleByte(ReadableFontData* rfd, ByteVector* buffer) {
+  buffer->resize(rfd->Length());
+  for (int32_t index = 0; index < rfd->Length(); ++index) {
+    (*buffer)[index] = (byte_t)(rfd->ReadByte(index));
+  }
+}
+
+void ReadFontDataWithBuffer(ReadableFontData* rfd,
+                            int32_t buffer_size,
+                            ByteVector* b) {
+  ByteVector buffer(buffer_size);
+  b->resize(rfd->Length());
+
+  int32_t index = 0;
+  while (index < rfd->Length()) {
+    int32_t bytes_read = rfd->ReadBytes(index, &(buffer[0]), 0, buffer.size());
+    EXPECT_GE(bytes_read, 0);
+    std::copy(buffer.begin(), buffer.begin() + bytes_read, b->begin() + index);
+    index += bytes_read;
+  }
+}
+
+void ReadFontDataWithSlidingWindow(ReadableFontData* rfd, int32_t window_size,
+                                   ByteVector* b) {
+  b->resize(rfd->Length());
+  int32_t index = 0;
+  while (index < rfd->Length()) {
+    int32_t actual_window_size =
+        std::min<int32_t>(window_size, b->size() - index);
+    int32_t bytes_read =
+        rfd->ReadBytes(index, &((*b)[0]), index, actual_window_size);
+    EXPECT_GE(bytes_read, 0);
+    index += bytes_read;
+  }
+}
+
+void WriteFontDataWithSingleByte(ReadableFontData* rfd, WritableFontData* wfd) {
+  for (int32_t index = 0; index < rfd->Length(); ++index) {
+    byte_t b = (byte_t)(rfd->ReadByte(index));
+    wfd->WriteByte(index, b);
+  }
+}
+
+void WriteFontDataWithBuffer(ReadableFontData* rfd,
+                             WritableFontData* wfd,
+                             int32_t buffer_size) {
+  ByteVector buffer(buffer_size);
+  int32_t index = 0;
+  while (index < rfd->Length()) {
+    int32_t bytesRead = rfd->ReadBytes(index, &(buffer[0]), 0, buffer.size());
+    wfd->WriteBytes(index, &(buffer[0]), 0, buffer.size());
+    index += bytesRead;
+  }
+}
+
+void WriteFontDataWithSlidingWindow(ReadableFontData* rfd,
+                                    WritableFontData* wfd,
+                                    int32_t window_size) {
+  ByteVector b(rfd->Length());
+  int32_t index = 0;
+  while (index < rfd->Length()) {
+    int32_t sliding_size = std::min<int32_t>(window_size, b.size() - index);
+    int32_t bytes_read = rfd->ReadBytes(index, &(b[0]), index, sliding_size);
+    wfd->WriteBytes(index, &(b[0]), index, sliding_size);
+    index += bytes_read;
+  }
+}
+
+bool ReadComparison(int32_t offset,
+                    int32_t length,
+                    ReadableFontData* rfd1,
+                    ReadableFontData* rfd2) {
+  EXPECT_TRUE(length == rfd2->Length());
+  ByteVector b1, b2;
+  b1.resize(length);
+  b2.resize(length);
+
+  // single byte reads
+  ReadFontDataWithSingleByte(rfd1, &b1);
+  ReadFontDataWithSingleByte(rfd2, &b2);
+  EXPECT_EQ(memcmp(&(b1[offset]), &(b2[0]), length), 0);
+
+  // buffer reads
+  int32_t increments = std::max<int32_t>(length / 11, 1);
+  for (int32_t buffer_size = 1; buffer_size <= length;
+       buffer_size += increments) {
+    b1.clear();
+    b2.clear();
+    b1.resize(length);
+    b2.resize(length);
+    ReadFontDataWithBuffer(rfd1, buffer_size, &b1);
+    ReadFontDataWithBuffer(rfd2, buffer_size, &b2);
+    int result = memcmp(&(b1[offset]), &(b2[0]), length);
+    EXPECT_EQ(result, 0);
+  }
+
+  // sliding window reads
+  for (int32_t window_size = 1; window_size <= length;
+       window_size += increments) {
+    b1.clear();
+    b2.clear();
+    b1.resize(length);
+    b2.resize(length);
+    ReadFontDataWithSlidingWindow(rfd1, window_size, &b1);
+    ReadFontDataWithSlidingWindow(rfd2, window_size, &b2);
+    int result = memcmp(&(b1[offset]), &(b2[0]), length);
+    EXPECT_EQ(result, 0);
+  }
+  return true;
+}
+
+void SlicingReadTest(ReadableFontData* rfd) {
+  fprintf(stderr, "read - trim = ");
+  for (int32_t trim = 0; trim < (rfd->Length() / 2) + 1;
+       trim += (rfd->Length() / 21) + 1) {
+    fprintf(stderr, "%d ", trim);
+    int32_t length = rfd->Length() - 2 * trim;
+    ReadableFontDataPtr slice;
+    slice.Attach(down_cast<ReadableFontData*>(rfd->Slice(trim, length)));
+    EXPECT_TRUE(ReadComparison(trim, length, rfd, slice));
+  }
+  fprintf(stderr, "\n");
+}
+
+void SlicingWriteTest(ReadableFontData* rfd, WritableFontData* wfd) {
+  fprintf(stderr, "write - trim = ");
+  for (int32_t trim = 0; trim < (rfd->Length() / 2) + 1;
+       trim += (rfd->Length() / 21) + 1) {
+    fprintf(stderr, "%d ", trim);
+    int32_t length = rfd->Length() - 2 * trim;
+    WritableFontDataPtr w_slice;
+    ReadableFontDataPtr r_slice;
+
+    // single byte writes
+    w_slice.Attach(down_cast<WritableFontData*>(wfd->Slice(trim, length)));
+    r_slice.Attach(down_cast<ReadableFontData*>(rfd->Slice(trim, length)));
+    WriteFontDataWithSingleByte(r_slice, w_slice);
+    EXPECT_TRUE(ReadComparison(trim, length, rfd, w_slice));
+
+    // buffer writes
+    int32_t increments = std::max<int32_t>(length / 11, 1);
+    for (int32_t buffer_size = 1; buffer_size < length;
+         buffer_size += increments) {
+      w_slice.Attach(down_cast<WritableFontData*>(wfd->Slice(trim, length)));
+      r_slice.Attach(down_cast<ReadableFontData*>(rfd->Slice(trim, length)));
+      WriteFontDataWithBuffer(r_slice, w_slice, buffer_size);
+      EXPECT_TRUE(ReadComparison(trim, length, rfd, w_slice));
+    }
+
+    // sliding window writes
+    for (int window_size = 1; window_size < length; window_size += increments) {
+      w_slice.Attach(down_cast<WritableFontData*>(wfd->Slice(trim, length)));
+      r_slice.Attach(down_cast<ReadableFontData*>(rfd->Slice(trim, length)));
+      WriteFontDataWithSlidingWindow(r_slice, w_slice, window_size);
+      EXPECT_TRUE(ReadComparison(trim, length, rfd, w_slice));
+    }
+  }
+  fprintf(stderr, "\n");
+}
+
+bool TestReadableFontData() {
+  for (size_t i = 0; i < sizeof(BYTE_ARRAY_SIZES) / sizeof(int32_t); ++i) {
+    int32_t size = BYTE_ARRAY_SIZES[i];
+    ByteArrayPtr ba = new MemoryByteArray(size);
+    FillTestByteArray(ba, size);
+    ReadableFontDataPtr rfd = new ReadableFontData(ba);
+    SlicingReadTest(rfd);
+  }
+  return true;
+}
+
+bool TestWritableFontData() {
+  for (size_t i = 0; i < sizeof(BYTE_ARRAY_SIZES) / sizeof(int32_t); ++i) {
+    int32_t size = BYTE_ARRAY_SIZES[i];
+    ByteArrayPtr ba = new MemoryByteArray(size);
+    FillTestByteArray(ba, size);
+    WritableFontDataPtr wfd = new WritableFontData(ba);
+    SlicingReadTest(wfd);
+    ByteArrayPtr temp = new MemoryByteArray(size);
+    WritableFontDataPtr wfd_copy = new WritableFontData(temp);
+    SlicingWriteTest(wfd, wfd_copy);
+  }
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(FontData, ReadableFontDataSearching) {
+  ASSERT_TRUE(sfntly::TestReadableFontDataSearching());
+}
+
+TEST(FontData, All) {
+  ASSERT_TRUE(sfntly::TestReadableFontData());
+  ASSERT_TRUE(sfntly::TestWritableFontData());
+}
diff --git a/sfntly/cpp/src/test/font_parsing_test.cc b/sfntly/cpp/src/test/font_parsing_test.cc
new file mode 100644
index 0000000..6fd5c3b
--- /dev/null
+++ b/sfntly/cpp/src/test/font_parsing_test.cc
@@ -0,0 +1,140 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+
+#include "sfntly/data/font_input_stream.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/font_header_table.h"
+#include "sfntly/table/table.h"
+#include "sfntly/table/generic_table_builder.h"
+#include "sfntly/table/table_based_table_builder.h"
+#include "sfntly/tag.h"
+#include "sfntly/port/file_input_stream.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+
+namespace sfntly {
+
+bool TestFontParsing() {
+  ByteVector input_buffer;
+  LoadFile(SAMPLE_TTF_FILE, &input_buffer);
+
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  // File based
+  FontBuilderArray font_builder_array;
+  BuilderForFontFile(SAMPLE_TTF_FILE, factory, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+  // Memory based
+  FontBuilderArray font_builder_array2;
+  factory->LoadFontsForBuilding(&input_buffer, &font_builder_array2);
+  FontBuilderPtr font_builder2 = font_builder_array2[0];
+
+  for (size_t i = 0; i < SAMPLE_TTF_KNOWN_TAGS; ++i) {
+    EXPECT_TRUE(font_builder->HasTableBuilder(TTF_KNOWN_TAGS[i]));
+    EXPECT_TRUE(font_builder2->HasTableBuilder(TTF_KNOWN_TAGS[i]));
+  }
+
+  // Generic table
+  Ptr<GenericTableBuilder> gdef_builder =
+      down_cast<GenericTableBuilder*>(font_builder->GetTableBuilder(Tag::feat));
+  HeaderPtr gdef_header = gdef_builder->header();
+  EXPECT_EQ(gdef_header->length(), TTF_LENGTH[SAMPLE_TTF_FEAT]);
+  EXPECT_EQ(gdef_header->offset(), TTF_OFFSET[SAMPLE_TTF_FEAT]);
+  EXPECT_EQ(gdef_header->checksum(), TTF_CHECKSUM[SAMPLE_TTF_FEAT]);
+  EXPECT_TRUE(gdef_header->checksum_valid());
+
+  WritableFontDataPtr wfd;
+  wfd.Attach(gdef_builder->Data());
+  ByteVector b;
+  b.resize(TTF_LENGTH[SAMPLE_TTF_FEAT]);
+  wfd->ReadBytes(0, &(b[0]), 0, TTF_LENGTH[SAMPLE_TTF_FEAT]);
+  EXPECT_EQ(memcmp(&(b[0]), TTF_FEAT_DATA, TTF_LENGTH[SAMPLE_TTF_FEAT]), 0);
+
+  // Header table
+  FontHeaderTableBuilderPtr header_builder =
+      down_cast<FontHeaderTable::Builder*>(
+          font_builder->GetTableBuilder(Tag::head));
+  HeaderPtr header_header = header_builder->header();
+  EXPECT_EQ(header_header->length(), TTF_LENGTH[SAMPLE_TTF_HEAD]);
+  EXPECT_EQ(header_header->offset(), TTF_OFFSET[SAMPLE_TTF_HEAD]);
+  EXPECT_EQ(header_header->checksum(), TTF_CHECKSUM[SAMPLE_TTF_HEAD]);
+  EXPECT_TRUE(header_header->checksum_valid());
+
+  // Data conformance
+  for (size_t i = 0; i < SAMPLE_TTF_KNOWN_TAGS; ++i) {
+    ByteVector b1, b2;
+    b1.resize(TTF_LENGTH[i]);
+    b2.resize(TTF_LENGTH[i]);
+    TableBuilderPtr builder1 =
+        font_builder->GetTableBuilder(TTF_KNOWN_TAGS[i]);
+    TableBuilderPtr builder2 =
+        font_builder2->GetTableBuilder(TTF_KNOWN_TAGS[i]);
+    WritableFontDataPtr wfd1;
+    wfd1.Attach(builder1->Data());
+    WritableFontDataPtr wfd2;
+    wfd2.Attach(builder2->Data());
+    wfd1->ReadBytes(0, &(b1[0]), 0, TTF_LENGTH[i]);
+    wfd2->ReadBytes(0, &(b2[0]), 0, TTF_LENGTH[i]);
+    EXPECT_EQ(memcmp(&(b1[0]), &(b2[0]), TTF_LENGTH[i]), 0);
+  }
+
+  return true;
+}
+
+bool TestTTFReadWrite() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  BuilderForFontFile(SAMPLE_TTF_FILE, factory, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+  FontPtr font;
+  font.Attach(font_builder->Build());
+  MemoryOutputStream output_stream;
+  factory->SerializeFont(font, &output_stream);
+  EXPECT_GE(output_stream.Size(), SAMPLE_TTF_SIZE);
+
+  return true;
+}
+
+bool TestTTFMemoryBasedReadWrite() {
+  ByteVector input_buffer;
+  LoadFile(SAMPLE_TTF_FILE, &input_buffer);
+
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  factory->LoadFontsForBuilding(&input_buffer, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+  FontPtr font;
+  font.Attach(font_builder->Build());
+  MemoryOutputStream output_stream;
+  factory->SerializeFont(font, &output_stream);
+  EXPECT_GE(output_stream.Size(), input_buffer.size());
+
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(FontParsing, All) {
+  ASSERT_TRUE(sfntly::TestFontParsing());
+  ASSERT_TRUE(sfntly::TestTTFReadWrite());
+  ASSERT_TRUE(sfntly::TestTTFMemoryBasedReadWrite());
+}
diff --git a/sfntly/cpp/src/test/hdmx_test.cc b/sfntly/cpp/src/test/hdmx_test.cc
new file mode 100644
index 0000000..cdc4ed0
--- /dev/null
+++ b/sfntly/cpp/src/test/hdmx_test.cc
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/table/core/horizontal_device_metrics_table.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+
+namespace sfntly {
+
+const int32_t HDMX_VERSION = 0;
+const int32_t HDMX_NUM_RECORDS = 4;
+const int32_t HDMX_RECORD_SIZE = 628;
+const int32_t HDMX_PIXEL_SIZE[] = {10, 11, 12, 13};
+const int32_t HDMX_MAX_WIDTH[] = {5, 6, 7, 7};
+
+bool TestReadingHdmxTable() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontArray font_array;
+  LoadFont(SAMPLE_BITMAP_FONT, factory, &font_array);
+  FontPtr font = font_array[0];
+
+  HorizontalDeviceMetricsTablePtr hdmx_table =
+      down_cast<HorizontalDeviceMetricsTable*>(font->GetTable(Tag::hdmx));
+
+  EXPECT_FALSE(hdmx_table == NULL);
+
+  EXPECT_EQ(hdmx_table->Version(), HDMX_VERSION);
+  EXPECT_EQ(hdmx_table->NumRecords(), HDMX_NUM_RECORDS);
+  EXPECT_EQ(hdmx_table->RecordSize(), HDMX_RECORD_SIZE);
+
+  for (int32_t i = 0; i < HDMX_NUM_RECORDS; ++i) {
+    EXPECT_EQ(hdmx_table->PixelSize(i), HDMX_PIXEL_SIZE[i]);
+    EXPECT_EQ(hdmx_table->MaxWidth(i), HDMX_MAX_WIDTH[i]);
+  }
+
+  EXPECT_EQ(hdmx_table->Width(0, 0), HDMX_MAX_WIDTH[0]);
+  EXPECT_EQ(hdmx_table->Width(0, 19), HDMX_MAX_WIDTH[0]);
+  EXPECT_EQ(hdmx_table->Width(0, 623), HDMX_MAX_WIDTH[0]);
+  EXPECT_EQ(hdmx_table->Width(1, 0), HDMX_MAX_WIDTH[1]);
+  EXPECT_EQ(hdmx_table->Width(1, 19), HDMX_MAX_WIDTH[1]);
+  EXPECT_EQ(hdmx_table->Width(1, 623), HDMX_MAX_WIDTH[1]);
+  EXPECT_EQ(hdmx_table->Width(2, 0), HDMX_MAX_WIDTH[2]);
+  EXPECT_EQ(hdmx_table->Width(2, 19), HDMX_MAX_WIDTH[2]);
+  EXPECT_EQ(hdmx_table->Width(2, 623), HDMX_MAX_WIDTH[2]);
+  EXPECT_EQ(hdmx_table->Width(3, 0), HDMX_MAX_WIDTH[3]);
+  EXPECT_EQ(hdmx_table->Width(3, 19), HDMX_MAX_WIDTH[3]);
+  EXPECT_EQ(hdmx_table->Width(3, 623), HDMX_MAX_WIDTH[3]);
+
+#if defined(SFNTLY_NO_EXCEPTION)
+  EXPECT_EQ(hdmx_table->PixelSize(4), -1);
+  EXPECT_EQ(hdmx_table->PixelSize(-1), -1);
+  EXPECT_EQ(hdmx_table->MaxWidth(4), -1);
+  EXPECT_EQ(hdmx_table->MaxWidth(-1), -1);
+  EXPECT_EQ(hdmx_table->Width(0, 624), -1);
+  EXPECT_EQ(hdmx_table->Width(1, -1), -1);
+  EXPECT_EQ(hdmx_table->Width(-1, 0), -1);
+  EXPECT_EQ(hdmx_table->Width(-1, -1), -1);
+#endif
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(HdmxTable, All) {
+  ASSERT_TRUE(sfntly::TestReadingHdmxTable());
+}
diff --git a/sfntly/cpp/src/test/lock_test.cc b/sfntly/cpp/src/test/lock_test.cc
new file mode 100644
index 0000000..b29a4bf
--- /dev/null
+++ b/sfntly/cpp/src/test/lock_test.cc
@@ -0,0 +1,244 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdlib.h>
+
+#include "gtest/gtest.h"
+#include "sfntly/port/lock.h"
+#include "test/platform_thread.h"
+
+namespace sfntly {
+
+// Basic test to make sure that Acquire()/Unlock()/Try() don't crash
+
+class BasicLockTestThread : public PlatformThread::Delegate {
+ public:
+  BasicLockTestThread(Lock* lock) : lock_(lock), acquired_(0) {}
+
+  virtual void ThreadMain() {
+    for (int i = 0; i < 10; i++) {
+      lock_->Acquire();
+      acquired_++;
+      lock_->Unlock();
+    }
+    for (int i = 0; i < 10; i++) {
+      lock_->Acquire();
+      acquired_++;
+      PlatformThread::Sleep(rand() % 20);
+      lock_->Unlock();
+    }
+    for (int i = 0; i < 10; i++) {
+      if (lock_->Try()) {
+        acquired_++;
+        PlatformThread::Sleep(rand() % 20);
+        lock_->Unlock();
+      }
+    }
+  }
+
+  int acquired() const { return acquired_; }
+
+ private:
+  Lock* lock_;
+  int acquired_;
+
+  NO_COPY_AND_ASSIGN(BasicLockTestThread);
+};
+
+bool BasicLockTest() {
+  Lock lock;
+  BasicLockTestThread thread(&lock);
+  PlatformThreadHandle handle = kNullThreadHandle;
+
+  EXPECT_TRUE(PlatformThread::Create(&thread, &handle));
+
+  int acquired = 0;
+  for (int i = 0; i < 5; i++) {
+    lock.Acquire();
+    acquired++;
+    lock.Unlock();
+  }
+  for (int i = 0; i < 10; i++) {
+    lock.Acquire();
+    acquired++;
+    PlatformThread::Sleep(rand() % 20);
+    lock.Unlock();
+  }
+  for (int i = 0; i < 10; i++) {
+    if (lock.Try()) {
+      acquired++;
+      PlatformThread::Sleep(rand() % 20);
+      lock.Unlock();
+    }
+  }
+  for (int i = 0; i < 5; i++) {
+    lock.Acquire();
+    acquired++;
+    PlatformThread::Sleep(rand() % 20);
+    lock.Unlock();
+  }
+
+  PlatformThread::Join(handle);
+
+  EXPECT_GE(acquired, 20);
+  EXPECT_GE(thread.acquired(), 20);
+
+  return true;
+}
+
+// Test that Try() works as expected -------------------------------------------
+
+class TryLockTestThread : public PlatformThread::Delegate {
+ public:
+  TryLockTestThread(Lock* lock) : lock_(lock), got_lock_(false) {}
+
+  virtual void ThreadMain() {
+    got_lock_ = lock_->Try();
+    if (got_lock_)
+      lock_->Unlock();
+  }
+
+  bool got_lock() const { return got_lock_; }
+
+ private:
+  Lock* lock_;
+  bool got_lock_;
+
+  NO_COPY_AND_ASSIGN(TryLockTestThread);
+};
+
+bool TryLockTest() {
+  Lock lock;
+
+  EXPECT_TRUE(lock.Try());
+  // We now have the lock....
+
+  // This thread will not be able to get the lock.
+  {
+    TryLockTestThread thread(&lock);
+    PlatformThreadHandle handle = kNullThreadHandle;
+
+    EXPECT_TRUE(PlatformThread::Create(&thread, &handle));
+
+    PlatformThread::Join(handle);
+
+    EXPECT_FALSE(thread.got_lock());
+  }
+
+  lock.Unlock();
+
+  // This thread will....
+  {
+    TryLockTestThread thread(&lock);
+    PlatformThreadHandle handle = kNullThreadHandle;
+
+    EXPECT_TRUE(PlatformThread::Create(&thread, &handle));
+
+    PlatformThread::Join(handle);
+
+    EXPECT_TRUE(thread.got_lock());
+    // But it released it....
+    EXPECT_TRUE(lock.Try());
+  }
+
+  lock.Unlock();
+  return true;
+}
+
+// Tests that locks actually exclude -------------------------------------------
+
+class MutexLockTestThread : public PlatformThread::Delegate {
+ public:
+  MutexLockTestThread(Lock* lock, int* value) : lock_(lock), value_(value) {}
+
+  // Static helper which can also be called from the main thread.
+  static void DoStuff(Lock* lock, int* value) {
+    for (int i = 0; i < 40; i++) {
+      lock->Acquire();
+      int v = *value;
+      PlatformThread::Sleep(rand() % 10);
+      *value = v + 1;
+      lock->Unlock();
+    }
+  }
+
+  virtual void ThreadMain() {
+    DoStuff(lock_, value_);
+  }
+
+ private:
+  Lock* lock_;
+  int* value_;
+
+  NO_COPY_AND_ASSIGN(MutexLockTestThread);
+};
+
+bool MutexTwoThreads() {
+  Lock lock;
+  int value = 0;
+
+  MutexLockTestThread thread(&lock, &value);
+  PlatformThreadHandle handle = kNullThreadHandle;
+
+  EXPECT_TRUE(PlatformThread::Create(&thread, &handle));
+
+  MutexLockTestThread::DoStuff(&lock, &value);
+
+  PlatformThread::Join(handle);
+
+  EXPECT_EQ(2 * 40, value);
+  return true;
+}
+
+bool MutexFourThreads() {
+  Lock lock;
+  int value = 0;
+
+  MutexLockTestThread thread1(&lock, &value);
+  MutexLockTestThread thread2(&lock, &value);
+  MutexLockTestThread thread3(&lock, &value);
+  PlatformThreadHandle handle1 = kNullThreadHandle;
+  PlatformThreadHandle handle2 = kNullThreadHandle;
+  PlatformThreadHandle handle3 = kNullThreadHandle;
+
+  EXPECT_TRUE(PlatformThread::Create(&thread1, &handle1));
+  EXPECT_TRUE(PlatformThread::Create(&thread2, &handle2));
+  EXPECT_TRUE(PlatformThread::Create(&thread3, &handle3));
+
+  MutexLockTestThread::DoStuff(&lock, &value);
+
+  PlatformThread::Join(handle1);
+  PlatformThread::Join(handle2);
+  PlatformThread::Join(handle3);
+
+  EXPECT_EQ(4 * 40, value);
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(LockTest, Basic) {
+  ASSERT_TRUE(sfntly::BasicLockTest());
+}
+
+TEST(LockTest, TryLock) {
+  ASSERT_TRUE(sfntly::TryLockTest());
+}
+
+TEST(LockTest, Mutex) {
+  ASSERT_TRUE(sfntly::MutexTwoThreads());
+  ASSERT_TRUE(sfntly::MutexFourThreads());
+}
diff --git a/sfntly/cpp/src/test/memory_io_test.cc b/sfntly/cpp/src/test/memory_io_test.cc
new file mode 100755
index 0000000..b34e1e7
--- /dev/null
+++ b/sfntly/cpp/src/test/memory_io_test.cc
@@ -0,0 +1,102 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+
+#include <algorithm>
+
+#include "gtest/gtest.h"
+#include "sfntly/port/memory_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "sfntly/port/type.h"
+
+namespace {
+  const char* kTestData =
+"01234567890123456789012345678901234567890123456789"  // 50
+"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwx"  // 100
+"yz";                                                 // 102
+  const size_t kTestBufferLen = 102;
+}
+
+namespace sfntly {
+
+bool TestMemoryInputStream() {
+  ByteVector test_buffer;
+  test_buffer.resize(kTestBufferLen);
+  std::copy(kTestData, kTestData + kTestBufferLen, test_buffer.begin());
+
+  MemoryInputStream is;
+  is.Attach(&(test_buffer[0]), kTestBufferLen);
+  EXPECT_EQ(is.Available(), (int32_t)kTestBufferLen);
+
+  // Read one byte
+  EXPECT_EQ(is.Read(), '0');  // position 1
+  EXPECT_EQ(is.Read(), '1');  // position 2
+  EXPECT_EQ(is.Read(), '2');  // position 3
+
+  // Read byte vector
+  ByteVector b;
+  b.resize(7);
+  EXPECT_EQ(is.Read(&b), 7);  // position 10
+  EXPECT_EQ(memcmp(&(b[0]), &(test_buffer[0]) + 3, 7), 0);
+
+  b.resize(17);
+  EXPECT_EQ(is.Read(&b, 7, 10), 10);  // position 20
+  EXPECT_EQ(memcmp(&(b[0]), &(test_buffer[0]) + 3, 17), 0);
+
+  // Test skip
+  b.clear();
+  b.resize(10);
+  EXPECT_EQ(is.Skip(30), 30);  // position 50
+  EXPECT_EQ(is.Read(&b), 10);  // position 60
+  EXPECT_EQ(memcmp(&(b[0]), &(test_buffer[0]) + 50, 10), 0);
+  b.clear();
+  b.resize(10);
+  EXPECT_EQ(is.Skip(-20), -20);  // position 40
+  EXPECT_EQ(is.Read(&b), 10);  // position 50
+  EXPECT_EQ(memcmp(&(b[0]), &(test_buffer[0]) + 40, 10), 0);
+
+  EXPECT_EQ(is.Available(), (int32_t)kTestBufferLen - 50);
+  EXPECT_EQ(is.Skip(-60), -50);  // Out of bound, position 0
+  EXPECT_EQ(is.Skip(kTestBufferLen + 10), (int32_t)kTestBufferLen);
+
+  b.clear();
+  b.resize(10);
+  is.Unread(&b);
+  EXPECT_EQ(memcmp(&(b[0]), &(test_buffer[0]) + kTestBufferLen - 10, 10), 0);
+
+  return true;
+}
+
+bool TestMemoryOutputStream() {
+  ByteVector test_buffer;
+  test_buffer.resize(kTestBufferLen);
+  std::copy(kTestData, kTestData + kTestBufferLen, test_buffer.begin());
+
+  MemoryOutputStream os;
+  os.Write(&(test_buffer[0]), (int32_t)50, (int32_t)(kTestBufferLen - 50));
+  EXPECT_EQ(os.Size(), kTestBufferLen - 50);
+  EXPECT_EQ(memcmp(os.Get(), &(test_buffer[0]) + 50, kTestBufferLen - 50), 0);
+
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(MemoryIO, All) {
+  ASSERT_TRUE(sfntly::TestMemoryInputStream());
+  ASSERT_TRUE(sfntly::TestMemoryOutputStream());
+}
diff --git a/sfntly/cpp/src/test/name_editing_test.cc b/sfntly/cpp/src/test/name_editing_test.cc
new file mode 100644
index 0000000..260d9d4
--- /dev/null
+++ b/sfntly/cpp/src/test/name_editing_test.cc
@@ -0,0 +1,242 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// Must include this before ICU to avoid stdint redefinition issue.
+#include "sfntly/port/type.h"
+
+#include <unicode/ustring.h>
+#include <unicode/unistr.h>
+
+#include "gtest/gtest.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/port/memory_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "sfntly/table/core/name_table.h"
+#include "sfntly/tag.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+
+namespace sfntly {
+
+static ByteVector input_buffer;
+
+void LoadTestFile(FontFactory* factory, FontBuilderArray* font_builders) {
+  assert(factory);
+  assert(font_builders);
+  if (input_buffer.empty()) {
+    LoadFile(SAMPLE_TTF_FILE, &input_buffer);
+  }
+  factory->LoadFontsForBuilding(&input_buffer, font_builders);
+}
+
+bool TestChangeOneName() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  LoadTestFile(factory, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+
+  NameTableBuilderPtr name_builder = down_cast<NameTable::Builder*>(
+      font_builder->GetTableBuilder(Tag::name));
+
+  // Change the font name.
+  NameEntryBuilderPtr neb =
+      name_builder->NameBuilder(PlatformId::kWindows,
+                                WindowsEncodingId::kUnicodeUCS2,
+                                WindowsLanguageId::kEnglish_UnitedStates,
+                                NameId::kFontFamilyName);
+  U_STRING_DECL(new_name, "Timothy", 7);
+  neb->SetName(new_name);
+
+  // Build the font.
+  FontPtr font;
+  font.Attach(font_builder->Build());
+
+  // Serialize and reload the serialized font.
+  MemoryOutputStream os;
+  factory->SerializeFont(font, &os);
+  MemoryInputStream is;
+  is.Attach(os.Get(), os.Size());
+  FontArray font_array;
+  factory->LoadFonts(&is, &font_array);
+  FontPtr new_font = font_array[0];
+
+  // Check the font name.
+  NameTablePtr name_table = down_cast<NameTable*>(font->GetTable(Tag::name));
+  UChar* name = name_table->Name(PlatformId::kWindows,
+                                 WindowsEncodingId::kUnicodeUCS2,
+                                 WindowsLanguageId::kEnglish_UnitedStates,
+                                 NameId::kFontFamilyName);
+  EXPECT_TRUE(name != NULL);
+  EXPECT_EQ(u_strcmp(name, new_name), 0);
+  delete[] name;
+  return true;
+}
+
+bool TestModifyNameTableAndRevert() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  LoadTestFile(factory, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+
+  NameTableBuilderPtr name_builder = down_cast<NameTable::Builder*>(
+      font_builder->GetTableBuilder(Tag::name));
+
+  // Change the font name.
+  NameEntryBuilderPtr neb =
+      name_builder->NameBuilder(PlatformId::kWindows,
+                                WindowsEncodingId::kUnicodeUCS2,
+                                WindowsLanguageId::kEnglish_UnitedStates,
+                                NameId::kFontFamilyName);
+  NameTable::NameEntry* neb_entry = neb->name_entry();
+  UChar* original_name = neb_entry->Name();
+  EXPECT_TRUE(original_name != NULL);
+
+  U_STRING_DECL(new_name, "Timothy", 7);
+  neb->SetName(new_name);
+  name_builder->RevertNames();
+
+  // Build the font.
+  FontPtr font;
+  font.Attach(font_builder->Build());
+
+  // Serialize and reload the serialized font.
+  MemoryOutputStream os;
+  factory->SerializeFont(font, &os);
+  MemoryInputStream is;
+  is.Attach(os.Get(), os.Size());
+  FontArray font_array;
+  factory->LoadFonts(&is, &font_array);
+  FontPtr new_font = font_array[0];
+
+  // Check the font name.
+  NameTablePtr name_table = down_cast<NameTable*>(font->GetTable(Tag::name));
+  UChar* name = name_table->Name(PlatformId::kWindows,
+                                 WindowsEncodingId::kUnicodeUCS2,
+                                 WindowsLanguageId::kEnglish_UnitedStates,
+                                 NameId::kFontFamilyName);
+
+  EXPECT_EQ(u_strcmp(name, original_name), 0);
+  delete[] name;
+  delete[] original_name;
+
+  return true;
+}
+
+bool TestRemoveOneName() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  LoadTestFile(factory, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+
+  NameTableBuilderPtr name_builder = down_cast<NameTable::Builder*>(
+      font_builder->GetTableBuilder(Tag::name));
+
+  EXPECT_TRUE(name_builder->Has(PlatformId::kWindows,
+                                WindowsEncodingId::kUnicodeUCS2,
+                                WindowsLanguageId::kEnglish_UnitedStates,
+                                NameId::kFontFamilyName));
+  EXPECT_TRUE(name_builder->Remove(PlatformId::kWindows,
+                                   WindowsEncodingId::kUnicodeUCS2,
+                                   WindowsLanguageId::kEnglish_UnitedStates,
+                                   NameId::kFontFamilyName));
+
+  // Build the font.
+  FontPtr font;
+  font.Attach(font_builder->Build());
+
+  // Serialize and reload the serialized font.
+  MemoryOutputStream os;
+  factory->SerializeFont(font, &os);
+  MemoryInputStream is;
+  is.Attach(os.Get(), os.Size());
+  FontArray font_array;
+  factory->LoadFonts(&is, &font_array);
+  FontPtr new_font = font_array[0];
+
+  // Check the font name.
+  NameTablePtr name_table = down_cast<NameTable*>(font->GetTable(Tag::name));
+  UChar* name = name_table->Name(PlatformId::kWindows,
+                                 WindowsEncodingId::kUnicodeUCS2,
+                                 WindowsLanguageId::kEnglish_UnitedStates,
+                                 NameId::kFontFamilyName);
+  EXPECT_TRUE(name == NULL);
+
+  return true;
+}
+
+// Note: Function is not implemented but the test case is built.  Uncomment
+//       when NameTable::clear() is implemented.
+/*
+bool TestClearAllNamesAndSetOne() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  LoadTestFile(factory, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+
+  NameTableBuilderPtr name_builder = down_cast<NameTable::Builder*>(
+      font_builder->GetTableBuilder(Tag::name));
+
+  EXPECT_GT(name_builder->builderCount(), 0);
+  name_builder->clear();
+  EXPECT_EQ(name_builder->builderCount(), 0);
+
+  // Change the font name.
+  NameEntryBuilderPtr neb =
+      name_builder->NameBuilder(PlatformId::kWindows,
+                                WindowsEncodingId::kUnicodeUCS2,
+                                WindowsLanguageId::kEnglish_UnitedStates,
+                                NameId::kFontFamilyName);
+  U_STRING_DECL(new_name, "Fred", 4);
+  neb->SetName(new_name);
+
+  // Build the font.
+  FontPtr font = font_builder->Build();
+
+  // Serialize and reload the serialized font.
+  MemoryOutputStream os;
+  factory->SerializeFont(font, &os);
+  FontArray font_array;
+  ByteArrayPtr new_ba = new MemoryByteArray(os.Get(), os.Size());
+  factory->LoadFonts(new_ba, &font_array);
+  FontPtr new_font = font_array[0];
+
+  // Check the font name.
+  NameTablePtr name_table = down_cast<NameTable*>(font->table(Tag::name));
+  UChar* name = name_table->Name(PlatformId::kWindows,
+                                 WindowsEncodingId::kUnicodeUCS2,
+                                 WindowsLanguageId::kEnglish_UnitedStates,
+                                 NameId::kFontFamilyName);
+  EXPECT_EQ(name_table->NameCount(), 1);
+  EXPECT_EQ(u_strcmp(name, new_name), 0);
+
+  delete[] name;
+  return true;
+}
+*/
+
+}  // namespace sfntly
+
+TEST(NameEditing, All) {
+  EXPECT_TRUE(sfntly::TestChangeOneName());
+  EXPECT_TRUE(sfntly::TestModifyNameTableAndRevert());
+  EXPECT_TRUE(sfntly::TestRemoveOneName());
+}
diff --git a/sfntly/cpp/src/test/open_type_data_test.cc b/sfntly/cpp/src/test/open_type_data_test.cc
new file mode 100644
index 0000000..0917aab
--- /dev/null
+++ b/sfntly/cpp/src/test/open_type_data_test.cc
@@ -0,0 +1,70 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/data/writable_font_data.h"
+#include "sfntly/data/memory_byte_array.h"
+
+namespace sfntly {
+
+const byte_t TEST_OTF_DATA[] =
+    {0xff, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01};
+
+bool TestOTFRead() {
+  ByteVector bytes;
+  for (size_t i = 0; i < sizeof(TEST_OTF_DATA) / sizeof(byte_t); ++i) {
+    bytes.push_back(TEST_OTF_DATA[i]);
+  }
+  ByteArrayPtr array = new MemoryByteArray(&(bytes[0]), bytes.size());
+  ReadableFontDataPtr data = new ReadableFontData(array);
+
+  EXPECT_EQ(-1, data->ReadByte(0));
+  EXPECT_EQ(0xff, data->ReadUByte(0));
+  EXPECT_EQ(0x01, data->ReadByte(1));
+  EXPECT_EQ(65281, data->ReadUShort(0));
+  EXPECT_EQ(-255, data->ReadShort(0));
+  EXPECT_EQ(16711937, data->ReadUInt24(0));
+  EXPECT_EQ(4278255873LL, data->ReadULong(0));
+  EXPECT_EQ(-16711423, data->ReadLong(0));
+  return true;
+}
+
+bool TestOTFCopy() {
+  ByteVector source_bytes(1024);
+  for (size_t i = 0; i < source_bytes.size(); ++i) {
+    source_bytes[i] = (byte_t)(i & 0xff);
+  }
+  ByteArrayPtr source_array = new MemoryByteArray(&(source_bytes[0]), 1024);
+  ReadableFontDataPtr source = new ReadableFontData(source_array);
+
+  ByteVector destination_bytes(1024);
+  ByteArrayPtr destination_array =
+      new MemoryByteArray(&(destination_bytes[0]), 1024);
+  WritableFontDataPtr destination = new WritableFontData(destination_array);
+
+  int32_t length = source->CopyTo(destination);
+  EXPECT_EQ(1024, length);
+  EXPECT_TRUE(std::equal(source_bytes.begin(), source_bytes.end(),
+                         destination_bytes.begin()));
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(OpenTypeData, All) {
+  ASSERT_TRUE(sfntly::TestOTFRead());
+  ASSERT_TRUE(sfntly::TestOTFCopy());
+}
diff --git a/sfntly/cpp/src/test/otf_basic_editing_test.cc b/sfntly/cpp/src/test/otf_basic_editing_test.cc
new file mode 100644
index 0000000..7388fac
--- /dev/null
+++ b/sfntly/cpp/src/test/otf_basic_editing_test.cc
@@ -0,0 +1,90 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/table/core/font_header_table.h"
+#include "sfntly/tag.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/port/endian.h"
+#include "sfntly/port/file_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+
+namespace sfntly {
+
+bool TestOTFBasicEditing() {
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  BuilderForFontFile(SAMPLE_TTF_FILE, factory, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+
+  // ensure the builder is not bogus
+  EXPECT_TRUE(font_builder != NULL);
+  TableBuilderMap* builder_map = font_builder->table_builders();
+  EXPECT_TRUE(builder_map != NULL);
+  IntegerSet builder_tags;
+  for (TableBuilderMap::iterator i = builder_map->begin(),
+                                 e = builder_map->end(); i != e; ++i) {
+    EXPECT_TRUE(i->second != NULL);
+    if (i->second == NULL) {
+      char tag[5] = {0};
+      int32_t value = ToBE32(i->first);
+      memcpy(tag, &value, 4);
+      fprintf(stderr, "tag %s does not have valid builder\n", tag);
+    } else {
+      builder_tags.insert(i->first);
+    }
+  }
+
+  FontHeaderTableBuilderPtr header_builder =
+      down_cast<FontHeaderTable::Builder*>(
+          font_builder->GetTableBuilder(Tag::head));
+  int64_t mod_date = header_builder->Modified();
+  header_builder->SetModified(mod_date + 1);
+  FontPtr font;
+  font.Attach(font_builder->Build());
+
+  // ensure every table had a builder
+  const TableMap* table_map = font->GetTableMap();
+  for (TableMap::const_iterator i = table_map->begin(), e = table_map->end();
+                                i != e; ++i) {
+    TablePtr table = (*i).second;
+    HeaderPtr header = table->header();
+    EXPECT_TRUE(builder_tags.find(header->tag()) != builder_tags.end());
+    builder_tags.erase(header->tag());
+  }
+  EXPECT_TRUE(builder_tags.empty());
+
+  FontHeaderTablePtr header =
+      down_cast<FontHeaderTable*>(font->GetTable(Tag::head));
+  int64_t after_mod_date = header->Modified();
+  EXPECT_EQ(mod_date + 1, after_mod_date);
+
+  // Checksum correctness of builder.
+  TablePtr post = font->GetTable(Tag::post);
+  EXPECT_EQ(post->CalculatedChecksum(), TTF_CHECKSUM[SAMPLE_TTF_POST]);
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(OTFBasicEditing, All) {
+  ASSERT_TRUE(sfntly::TestOTFBasicEditing());
+}
diff --git a/sfntly/cpp/src/test/platform_thread.cc b/sfntly/cpp/src/test/platform_thread.cc
new file mode 100644
index 0000000..6a0b84b
--- /dev/null
+++ b/sfntly/cpp/src/test/platform_thread.cc
@@ -0,0 +1,101 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "test/platform_thread.h"
+
+namespace sfntly {
+
+#if defined (WIN32)
+
+DWORD __stdcall ThreadFunc(void* params) {
+  PlatformThread::Delegate* delegate =
+      static_cast<PlatformThread::Delegate*>(params);
+  delegate->ThreadMain();
+  return 0;
+}
+
+// static
+bool PlatformThread::Create(Delegate* delegate,
+                            PlatformThreadHandle* thread_handle) {
+  assert(thread_handle);
+  *thread_handle = CreateThread(NULL, 0, ThreadFunc, delegate, 0, NULL);
+  if (!(*thread_handle)) {
+    return false;
+  }
+
+  return true;
+}
+
+// static
+void PlatformThread::Join(PlatformThreadHandle thread_handle) {
+  assert(thread_handle);
+  DWORD result = WaitForSingleObject(thread_handle, INFINITE);
+  assert(result == WAIT_OBJECT_0);
+  CloseHandle(thread_handle);
+}
+
+// static
+void PlatformThread::Sleep(int32_t duration_ms) {
+  ::Sleep(duration_ms);
+}
+
+#else
+
+void* ThreadFunc(void* params) {
+  PlatformThread::Delegate* delegate =
+      static_cast<PlatformThread::Delegate*>(params);
+  delegate->ThreadMain();
+  return NULL;
+}
+
+// static
+bool PlatformThread::Create(Delegate* delegate,
+                            PlatformThreadHandle* thread_handle) {
+  assert(thread_handle);
+
+  bool success = false;
+  pthread_attr_t attributes;
+  pthread_attr_init(&attributes);
+  success = !pthread_create(thread_handle, &attributes, ThreadFunc, delegate);
+  pthread_attr_destroy(&attributes);
+
+  return success;
+}
+
+// static
+void PlatformThread::Join(PlatformThreadHandle thread_handle) {
+  assert(thread_handle);
+  pthread_join(thread_handle, NULL);
+}
+
+// static
+void PlatformThread::Sleep(int32_t duration_ms) {
+  struct timespec sleep_time, remaining;
+
+  // Contains the portion of duration_ms >= 1 sec.
+  sleep_time.tv_sec = duration_ms / 1000;
+  duration_ms -= sleep_time.tv_sec * 1000;
+
+  // Contains the portion of duration_ms < 1 sec.
+  sleep_time.tv_nsec = duration_ms * 1000 * 1000;  // nanoseconds.
+
+  while (nanosleep(&sleep_time, &remaining) == -1 && errno == EINTR)
+    sleep_time = remaining;
+}
+
+#endif  // WIN32
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/platform_thread.h b/sfntly/cpp/src/test/platform_thread.h
new file mode 100644
index 0000000..f236f4c
--- /dev/null
+++ b/sfntly/cpp/src/test/platform_thread.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// Simple platform thread implementation used to test our cross-platform locks.
+// This is a trimmed down version of Chromium base/threading/platform_thread.h.
+
+#ifndef SFNTLY_CPP_SRC_TEST_PLATFORM_THREAD_H_
+#define SFNTLY_CPP_SRC_TEST_PLATFORM_THREAD_H_
+
+#if defined (WIN32)
+#include <windows.h>
+#else  // Assume pthread
+#include <errno.h>
+#include <pthread.h>
+#include <time.h>
+#endif // if defined (WIN32)
+
+#include "sfntly/port/type.h"
+
+namespace sfntly {
+
+#if defined (WIN32)
+typedef HANDLE PlatformThreadHandle;
+const PlatformThreadHandle kNullThreadHandle = NULL;
+#else  // Assume pthread
+typedef pthread_t PlatformThreadHandle;
+const PlatformThreadHandle kNullThreadHandle = 0;
+#endif
+
+class PlatformThread {
+ public:
+  class Delegate {
+   public:
+     virtual ~Delegate() {}
+     virtual void ThreadMain() = 0;
+  };
+
+  // Sleeps for the specified duration (units are milliseconds).
+  static void Sleep(int32_t duration_ms);
+
+  // Creates a new thread using default stack size.  Upon success,
+  // |*thread_handle| will be assigned a handle to the newly created thread,
+  // and |delegate|'s ThreadMain method will be executed on the newly created
+  // thread.
+  // NOTE: When you are done with the thread handle, you must call Join to
+  // release system resources associated with the thread.  You must ensure that
+  // the Delegate object outlives the thread.
+  static bool Create(Delegate* delegate, PlatformThreadHandle* thread_handle);
+
+  // Joins with a thread created via the Create function.  This function blocks
+  // the caller until the designated thread exits.  This will invalidate
+  // |thread_handle|.
+  static void Join(PlatformThreadHandle thread_handle);
+
+private:
+  PlatformThread() {}
+  NO_COPY_AND_ASSIGN(PlatformThread);
+};
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_TEST_PLATFORM_THREAD_H_
diff --git a/sfntly/cpp/src/test/serialization_test.cc b/sfntly/cpp/src/test/serialization_test.cc
new file mode 100755
index 0000000..0f2f489
--- /dev/null
+++ b/sfntly/cpp/src/test/serialization_test.cc
@@ -0,0 +1,151 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/port/memory_input_stream.h"
+#include "sfntly/port/memory_output_stream.h"
+#include "test/test_data.h"
+#include "test/test_font_utils.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+bool TestSerialization() {
+  FontFactoryPtr factory1, factory2, factory3;
+  factory1.Attach(FontFactory::GetInstance());
+  FontArray font_array;
+  LoadFont(SAMPLE_TTF_FILE, factory1, &font_array);
+  FontPtr original = font_array[0];
+
+  factory2.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  BuilderForFontFile(SAMPLE_TTF_FILE, factory2, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+
+  FontPtr intermediate;
+  intermediate.Attach(font_builder->Build());
+  MemoryOutputStream os;
+  factory2->SerializeFont(intermediate, &os);
+
+  factory3.Attach(FontFactory::GetInstance());
+  FontArray new_font_array;
+  MemoryInputStream is;
+  is.Attach(os.Get(), os.Size());
+  factory3->LoadFonts(&is, &new_font_array);
+  FontPtr serialized = new_font_array[0];
+
+  // Check number of tables
+  EXPECT_EQ(original->num_tables(), serialized->num_tables());
+
+  // Check if same set of tables
+  const TableMap* original_tables = original->GetTableMap();
+  const TableMap* serialized_tables = serialized->GetTableMap();
+  EXPECT_EQ(original_tables->size(), serialized_tables->size());
+  TableMap::const_iterator not_found = serialized_tables->end();
+  for (TableMap::const_iterator b = original_tables->begin(),
+                                e = original_tables->end(); b != e; ++b) {
+    EXPECT_TRUE((serialized_tables->find(b->first) != not_found));
+  }
+
+  // TODO(arthurhsu): check cmap equivalence
+  // Check checksum equivalence
+  for (size_t i = 0; i < SAMPLE_TTF_KNOWN_TAGS; ++i) {
+      TablePtr original_table = original->GetTable(TTF_KNOWN_TAGS[i]);
+      TablePtr serialized_table = serialized->GetTable(TTF_KNOWN_TAGS[i]);
+    EXPECT_EQ(original_table->CalculatedChecksum(),
+              serialized_table->CalculatedChecksum());
+    EXPECT_EQ(original_table->DataLength(), serialized_table->DataLength());
+
+    if (TTF_KNOWN_TAGS[i] == Tag::hhea) {
+      EXPECT_TRUE(VerifyHHEA(original_table, serialized_table));
+    } else if (TTF_KNOWN_TAGS[i] == Tag::glyf) {
+        EXPECT_TRUE(VerifyGLYF(original_table, serialized_table));
+    } else if (TTF_KNOWN_TAGS[i] == Tag::hmtx) {
+        EXPECT_TRUE(VerifyHMTX(original_table, serialized_table));
+    } else if (TTF_KNOWN_TAGS[i] == Tag::loca) {
+        EXPECT_TRUE(VerifyLOCA(original_table, serialized_table));
+    } else if (TTF_KNOWN_TAGS[i] == Tag::maxp) {
+        EXPECT_TRUE(VerifyMAXP(original_table, serialized_table));
+    } else if (TTF_KNOWN_TAGS[i] == Tag::name) {
+        EXPECT_TRUE(VerifyNAME(original_table, serialized_table));
+    } else if (TTF_KNOWN_TAGS[i] == Tag::OS_2) {
+        EXPECT_TRUE(VerifyOS_2(original_table, serialized_table));
+    }
+  }
+
+  return true;
+}
+
+bool TestSerializationBitmap() {
+  FontFactoryPtr factory1, factory2, factory3;
+  factory1.Attach(FontFactory::GetInstance());
+  FontArray font_array;
+  LoadFont(SAMPLE_BITMAP_FONT, factory1, &font_array);
+  FontPtr original = font_array[0];
+
+  factory2.Attach(FontFactory::GetInstance());
+  FontBuilderArray font_builder_array;
+  BuilderForFontFile(SAMPLE_BITMAP_FONT, factory2, &font_builder_array);
+  FontBuilderPtr font_builder = font_builder_array[0];
+
+  FontPtr intermediate;
+  intermediate.Attach(font_builder->Build());
+  MemoryOutputStream os;
+  factory2->SerializeFont(intermediate, &os);
+
+  factory3.Attach(FontFactory::GetInstance());
+  FontArray new_font_array;
+  MemoryInputStream is;
+  is.Attach(os.Get(), os.Size());
+  factory3->LoadFonts(&is, &new_font_array);
+  FontPtr serialized = new_font_array[0];
+
+  // Check number of tables
+  EXPECT_EQ(original->num_tables(), serialized->num_tables());
+
+  // Check if same set of tables
+  const TableMap* original_tables = original->GetTableMap();
+  const TableMap* serialized_tables = serialized->GetTableMap();
+  EXPECT_EQ(original_tables->size(), serialized_tables->size());
+  TableMap::const_iterator not_found = serialized_tables->end();
+  for (TableMap::const_iterator b = original_tables->begin(),
+                                e = original_tables->end(); b != e; ++b) {
+    EXPECT_TRUE((serialized_tables->find(b->first) != not_found));
+  }
+
+  // Check checksum equivalence
+  for (size_t i = 0; i < SAMPLE_BITMAP_KNOWN_TAGS; ++i) {
+      TablePtr original_table = original->GetTable(BITMAP_KNOWN_TAGS[i]);
+      TablePtr serialized_table = serialized->GetTable(BITMAP_KNOWN_TAGS[i]);
+    EXPECT_EQ(original_table->CalculatedChecksum(),
+              serialized_table->CalculatedChecksum());
+    EXPECT_EQ(original_table->DataLength(), serialized_table->DataLength());
+  }
+
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(Serialization, Simple) {
+  ASSERT_TRUE(sfntly::TestSerialization());
+}
+
+TEST(Serialization, Bitmap) {
+  ASSERT_TRUE(sfntly::TestSerializationBitmap());
+}
diff --git a/sfntly/cpp/src/test/serialization_test.h b/sfntly/cpp/src/test/serialization_test.h
new file mode 100644
index 0000000..8996793
--- /dev/null
+++ b/sfntly/cpp/src/test/serialization_test.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_TEST_SERIALIZATION_TEST_H_
+#define SFNTLY_CPP_SRC_TEST_SERIALIZATION_TEST_H_
+
+#include "sfntly/table/table.h"
+
+namespace sfntly {
+
+bool VerifyHHEA(Table* original, Table* target);
+bool VerifyGLYF(Table* original, Table* target);
+bool VerifyHMTX(Table* original, Table* target);
+bool VerifyLOCA(Table* original, Table* target);
+bool VerifyMAXP(Table* original, Table* target);
+bool VerifyNAME(Table* original, Table* target);
+bool VerifyOS_2(Table* original, Table* target);
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_TEST_SERIALIZATION_TEST_H_
diff --git a/sfntly/cpp/src/test/smart_pointer_test.cc b/sfntly/cpp/src/test/smart_pointer_test.cc
new file mode 100644
index 0000000..9e81baa
--- /dev/null
+++ b/sfntly/cpp/src/test/smart_pointer_test.cc
@@ -0,0 +1,79 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#define ENABLE_OBJECT_COUNTER
+#include "sfntly/port/refcount.h"
+
+using sfntly::RefCounted;
+using sfntly::Ptr;
+
+class Foo : public RefCounted<Foo> {
+public:  // put in something to make sure it's not empty
+  int foo_;
+  int foo() { return foo_; }
+};
+
+bool TestSmartPointer() {
+  // scope out allocation
+  {
+    Ptr<Foo> p1;
+    p1 = new Foo();
+    EXPECT_EQ(size_t(1), p1->ref_count_);
+    EXPECT_EQ(size_t(1), RefCounted<Foo>::object_counter_);
+
+    Ptr<Foo> p2;
+    p2 = p1;
+    EXPECT_EQ(size_t(2), p1->ref_count_);
+    EXPECT_EQ(size_t(2), p2->ref_count_);
+    EXPECT_EQ(size_t(1), RefCounted<Foo>::object_counter_);
+
+    Ptr<Foo> p3;
+    p3 = p1;
+    EXPECT_EQ(size_t(3), p1->ref_count_);
+    EXPECT_EQ(size_t(3), p2->ref_count_);
+    EXPECT_EQ(size_t(3), p3->ref_count_);
+    EXPECT_EQ(size_t(1), RefCounted<Foo>::object_counter_);
+
+    p2 = new Foo();
+    EXPECT_EQ(size_t(2), p1->ref_count_);
+    EXPECT_EQ(size_t(1), p2->ref_count_);
+    EXPECT_EQ(size_t(2), p3->ref_count_);
+    EXPECT_EQ(size_t(2), RefCounted<Foo>::object_counter_);
+
+    p3.Release();
+    EXPECT_EQ(size_t(1), p1->ref_count_);
+    EXPECT_EQ(NULL, p3.p_);
+    EXPECT_EQ(size_t(2), RefCounted<Foo>::object_counter_);
+
+    p2 = NULL;
+    EXPECT_EQ(size_t(1), RefCounted<Foo>::object_counter_);
+
+    p1 = p1;
+    EXPECT_EQ(size_t(1), p1->ref_count_);
+    EXPECT_EQ(size_t(1), RefCounted<Foo>::object_counter_);
+
+    p1 = &(*p1);
+    EXPECT_EQ(size_t(1), p1->ref_count_);
+    EXPECT_EQ(size_t(1), RefCounted<Foo>::object_counter_);
+  }
+  EXPECT_EQ(size_t(0), RefCounted<Foo>::object_counter_);
+  return true;
+}
+
+TEST(SmartPointer, All) {
+  ASSERT_TRUE(TestSmartPointer());
+}
diff --git a/sfntly/cpp/src/test/test_data.cc b/sfntly/cpp/src/test/test_data.cc
new file mode 100644
index 0000000..05bc759
--- /dev/null
+++ b/sfntly/cpp/src/test/test_data.cc
@@ -0,0 +1,75 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/tag.cc"
+#include "test/test_data.h"
+
+namespace sfntly {
+
+// If the TTF file used in test changed, the verify*.cc in test need to be
+// changed also.
+// TODO(arthurhsu): Refactor this into a test class and have all const inside.
+//                  This way we can test multiple fonts using same set of
+//                  code.
+
+const char* SAMPLE_TTF_FILE = "Tuffy.ttf";
+const char* SAMPLE_BITMAP_FONT = "AnonymousPro-Regular.ttf";
+
+const size_t SAMPLE_TTF_SIZE = 183936;
+const size_t SAMPLE_TTF_TABLES = 17;
+const size_t SAMPLE_TTF_KNOWN_TAGS = 16;
+const size_t SAMPLE_BITMAP_KNOWN_TAGS = 20;
+const size_t SAMPLE_TTF_FEAT = 3;
+const size_t SAMPLE_TTF_HEAD = 6;
+const size_t SAMPLE_TTF_POST = 14;
+
+const int32_t TTF_KNOWN_TAGS[] = {
+    Tag::OS_2, Tag::cmap, Tag::cvt,  Tag::feat, Tag::gasp,
+    Tag::glyf, Tag::head, Tag::hhea, Tag::hmtx, Tag::kern,
+    Tag::loca, Tag::maxp, Tag::morx, Tag::name, Tag::post,
+    Tag::prop };
+
+const int32_t BITMAP_KNOWN_TAGS[] = {
+    Tag::EBDT, Tag::EBLC, Tag::EBSC, Tag::LTSH, Tag::OS_2,
+    Tag::VDMX, Tag::cmap, Tag::cvt,  Tag::fpgm, Tag::gasp,
+    Tag::glyf, Tag::hdmx, Tag::head, Tag::hhea, Tag::hmtx,
+    Tag::loca, Tag::maxp, Tag::name, Tag::post, Tag::prep };
+
+const int64_t TTF_CHECKSUM[] = {
+    0xD463FC48, 0x252028D1, 0x0065078A, 0xC01407B5, 0xFFFF0003,
+    0x9544342B, 0xFC8F16AD, 0x0EC30C7A, 0xA029CD5D, 0x32513087,
+    0x05C323B0, 0x06320195, 0x3B67E701, 0xE7DB08F3, 0xD46E5E89,
+    0xE6EB4A27 };
+
+const int64_t TTF_OFFSET[] = {
+    0x00000198, 0x00001964, 0x000025B0, 0x0002CA74, 0x0002C854,
+    0x00003D34, 0x0000011C, 0x00000154, 0x000001F0, 0x000245D8,
+    0x000025B8, 0x00000178, 0x0002CAB4, 0x00024860, 0x00028854,
+    0x0002C85C };
+
+const int32_t TTF_LENGTH[] = {
+            86,       3146,          8,         64,          8,
+        133284,         54,         36,       6002,        648,
+          6012,         32,        944,      16371,      16383,
+           536 };
+
+const unsigned char TTF_FEAT_DATA[] = {
+    0, 1, 0, 0, 0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1,
+    0, 0, 0, 0x30, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0x34,
+    0, 0, 1, 1, 0, 0xB, 0, 2, 0, 0, 0, 0x38, 0xC0, 0, 1, 2,
+    0, 0, 1, 3, 0, 2, 1, 4, 0, 0, 1, 5, 0, 2, 1, 6 };
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/test_data.h b/sfntly/cpp/src/test/test_data.h
new file mode 100644
index 0000000..d5e576f
--- /dev/null
+++ b/sfntly/cpp/src/test/test_data.h
@@ -0,0 +1,44 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_TEST_TEST_DATA_H_
+#define SFNTLY_CPP_SRC_TEST_TEST_DATA_H_
+
+#include "sfntly/tag.h"
+
+namespace sfntly {
+
+extern const char* SAMPLE_TTF_FILE;
+extern const char* SAMPLE_BITMAP_FONT;
+
+extern const size_t SAMPLE_TTF_SIZE;
+extern const size_t SAMPLE_TTF_TABLES;
+extern const size_t SAMPLE_TTF_KNOWN_TAGS;
+extern const size_t SAMPLE_BITMAP_KNOWN_TAGS;
+extern const size_t SAMPLE_TTF_FEAT;
+extern const size_t SAMPLE_TTF_HEAD;
+extern const size_t SAMPLE_TTF_POST;
+
+extern const int32_t TTF_KNOWN_TAGS[];
+extern const int32_t BITMAP_KNOWN_TAGS[];
+extern const int64_t TTF_CHECKSUM[];
+extern const int64_t TTF_OFFSET[];
+extern const int32_t TTF_LENGTH[];
+extern const unsigned char TTF_FEAT_DATA[];
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_TEST_TEST_DATA_H_
diff --git a/sfntly/cpp/src/test/test_font_utils.cc b/sfntly/cpp/src/test/test_font_utils.cc
new file mode 100644
index 0000000..d59b52b
--- /dev/null
+++ b/sfntly/cpp/src/test/test_font_utils.cc
@@ -0,0 +1,115 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+
+#include "gtest/gtest.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/data/growable_memory_byte_array.h"
+#include "sfntly/port/file_input_stream.h"
+#include "test/test_font_utils.h"
+
+namespace sfntly {
+
+void BuilderForFontFile(const char* font_path, FontFactory* factory,
+                        FontBuilderArray* builders) {
+  assert(factory);
+  FileInputStream is;
+  is.Open(font_path);
+  factory->LoadFontsForBuilding(&is, builders);
+  EXPECT_GT(builders->size(), static_cast<size_t>(0));
+}
+
+void SerializeFont(const char* font_path, FontFactory* factory, Font* font) {
+  assert(font_path);
+  assert(factory);
+  assert(font);
+  MemoryOutputStream output_stream;
+  factory->SerializeFont(font, &output_stream);
+  SerializeToFile(&output_stream, font_path);
+}
+
+void LoadFont(const char* font_path, FontFactory* factory, FontArray* fonts) {
+  FileInputStream is;
+  is.Open(font_path);
+  factory->LoadFonts(&is, fonts);
+  is.Close();
+}
+
+void LoadFontUsingByteVector(const char* font_path,
+                            bool fingerprint,
+                            FontArray* fonts) {
+  ByteVector bv;
+  LoadFile(font_path, &bv);
+  FontFactoryPtr factory;
+  factory.Attach(FontFactory::GetInstance());
+  factory->FingerprintFont(fingerprint);
+  factory->LoadFonts(&bv, fonts);
+}
+
+void LoadFile(const char* input_file_path, ByteVector* input_buffer) {
+  assert(input_file_path);
+  assert(input_buffer);
+
+  FILE* input_file = NULL;
+#if defined WIN32
+  fopen_s(&input_file, input_file_path, "rb");
+#else
+  input_file = fopen(input_file_path, "rb");
+#endif
+  EXPECT_NE(input_file, reinterpret_cast<FILE*>(NULL));
+  fseek(input_file, 0, SEEK_END);
+  size_t file_size = ftell(input_file);
+  fseek(input_file, 0, SEEK_SET);
+  input_buffer->resize(file_size);
+  size_t bytes_read = fread(&((*input_buffer)[0]), 1, file_size, input_file);
+  EXPECT_EQ(bytes_read, file_size);
+  fclose(input_file);
+}
+
+void SerializeToFile(MemoryOutputStream* output_stream, const char* file_path) {
+  assert(file_path);
+  assert(output_stream);
+
+  FILE* output_file = NULL;
+#if defined WIN32
+  fopen_s(&output_file, file_path, "wb");
+#else
+  output_file = fopen(file_path, "wb");
+#endif
+  EXPECT_NE(output_file, reinterpret_cast<FILE*>(NULL));
+  fwrite(output_stream->Get(), 1, output_stream->Size(), output_file);
+  fflush(output_file);
+  fclose(output_file);
+}
+
+void HexDump(const unsigned char* byte_data, size_t length) {
+  if (byte_data == NULL || length == 0) {
+    fprintf(stderr, "<NULL>\n");
+    return;
+  }
+
+  fprintf(stderr, "data length = %ld (%lx)\n", length, length);
+  for (size_t i = 0; i < length; ++i) {
+    fprintf(stderr, "%02x ", byte_data[i]);
+    if ((i & 0xf) == 0xf) {
+      fprintf(stderr, "\n");
+    }
+  }
+  fprintf(stderr, "\n");
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/test_font_utils.h b/sfntly/cpp/src/test/test_font_utils.h
new file mode 100644
index 0000000..57fde7a
--- /dev/null
+++ b/sfntly/cpp/src/test/test_font_utils.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_TEST_TEST_FONT_UTILS_H_
+#define SFNTLY_CPP_SRC_TEST_TEST_FONT_UTILS_H_
+
+#include "sfntly/font.h"
+#include "sfntly/font_factory.h"
+#include "sfntly/port/memory_output_stream.h"
+
+namespace sfntly {
+
+void BuilderForFontFile(const char* font_path, FontFactory* factory,
+                        FontBuilderArray* builders);
+void SerializeFont(const char* font_path, FontFactory* factory, Font* font);
+void LoadFont(const char* font_path, FontFactory* factory, FontArray* fonts);
+void LoadFontUsingByteVector(const char* font_path,
+                            bool fingerprint,
+                            FontArray* fonts);
+
+void LoadFile(const char* input_file_path, ByteVector* input_buffer);
+void SerializeToFile(MemoryOutputStream* output_stream, const char* file_path);
+
+void HexDump(const unsigned char* byte_data, size_t length);
+
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_TEST_TEST_FONT_UTILS_H_
diff --git a/sfntly/cpp/src/test/test_utils.cc b/sfntly/cpp/src/test/test_utils.cc
new file mode 100644
index 0000000..4751b92
--- /dev/null
+++ b/sfntly/cpp/src/test/test_utils.cc
@@ -0,0 +1,89 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "test/test_utils.h"
+
+#include <stdio.h>
+#include <unicode/ucnv.h>
+#include <unicode/uchar.h>
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/data/memory_byte_array.h"
+#include "sfntly/data/growable_memory_byte_array.h"
+#include "sfntly/port/file_input_stream.h"
+
+namespace sfntly {
+TestUtils::TestUtils() {}
+
+// static
+// OutputStream CreateOutputStream(const char *file_path) {
+// }
+
+// static
+// void TestUtils::CreateNewFile(const char* file_path) {
+// }
+
+// static
+int32_t TestUtils::EncodeOneChar(UConverter* encoder, int16_t uchar) {
+  char* target = new char[ucnv_getMaxCharSize(encoder) * 2];
+  char* target_end;
+  UChar* source = new UChar[2];
+  UChar* source_end;
+  source[0] = (UChar)uchar;
+  source[1] = 0;
+  UErrorCode status = U_ZERO_ERROR;
+  source_end = source;
+  target_end = target;
+  ucnv_fromUnicode(encoder, &target_end, target + 4,
+                   (const UChar**)&source_end, source + sizeof(UChar),
+                   NULL, TRUE, &status);
+  if (!U_SUCCESS(status)) {
+    fprintf(stderr, "Error occured in conversion of %d: %s\n",
+            uchar, u_errorName(status));
+    delete[] source;
+    delete[] target;
+    return 0;
+  }
+  int32_t enc_char = 0;
+  for (int32_t position = 0; position < target_end - target; ++position) {
+    enc_char <<= 8;
+    enc_char |= (target[position] & 0xff);
+  }
+  delete[] source;
+  delete[] target;
+  return enc_char;
+}
+
+// static
+UConverter* TestUtils::GetEncoder(const char* charset_name) {
+  if (charset_name == NULL || strcmp(charset_name, "") == 0)
+    return NULL;
+  UErrorCode status = U_ZERO_ERROR;
+  UConverter* conv = ucnv_open(charset_name, &status);
+  // if (!U_SUCCESS(status))
+  //   return NULL;
+  return conv;  // returns NULL @ error anyway
+}
+
+// Get a file's extension
+// static
+const char* TestUtils::Extension(const char* file_path) {
+  if (!file_path)
+    return NULL;
+  return strrchr(file_path, EXTENSION_SEPARATOR);
+}
+}
diff --git a/sfntly/cpp/src/test/test_utils.h b/sfntly/cpp/src/test/test_utils.h
new file mode 100644
index 0000000..af3ffd6
--- /dev/null
+++ b/sfntly/cpp/src/test/test_utils.h
@@ -0,0 +1,110 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef SFNTLY_CPP_SRC_TEST_TEST_UTILS_H_
+#define SFNTLY_CPP_SRC_TEST_TEST_UTILS_H_
+
+// Must include this before ICU to avoid stdint redefinition issue.
+#include "sfntly/port/type.h"
+
+#include <unicode/ucnv.h>
+
+#include <string>
+
+#include "sfntly/font.h"
+#include "sfntly/data/memory_byte_array.h"
+
+namespace sfntly {
+class TestUtils {
+  TestUtils();
+
+ public:
+  // Compare sections of two byte arrays for equality
+  // @param b1 byte array 1
+  // @param offset1 offset for comparison in byte array 1
+  // @param b2 byte array 2
+  // @param offset2 offset for comparison in byte array 2
+  // @param length the length of the byte arrays to compare
+  // @return true if the array segments are equal; false otherwise
+  // TODO(dfilimon): implement
+  static bool Equals(ByteArray* b1,
+                     int32_t offset1,
+                     ByteArray* b2,
+                     int32_t offset2);
+
+  // @param offset1 offset to start comparing the first ByteArray from
+  // @param ba1 the first ByteArray
+  // @param offset2 offset to start comparing the second ByteArray from
+  // @param ba2 the second ByteArray
+  // @param length the number of bytes to compare
+  // @return true if all bytes in the ranges given are equal; false otherwise
+  // TODO(dfilimon): implement
+  static bool Equals(ByteArray* b1,
+                     int32_t offset1,
+                     ByteArray* b2,
+                     int32_t offset2,
+                     int32_t length);
+
+  // TODO(dfilimon): implement FileOutputStream in port/file_output_stream.*
+  // static OutputStream createOutputStream(const char* file_path);
+
+  // TODO(dfilimon): adapt & implement
+  // static FileChannel createFilechannelForWriting(File file);
+
+  // Creates a new file including deleting an already existing file with the
+  // same path and name and creating any needed directories.
+  // TODO(dfilimon): implement
+  static void CreateNewFile(const char* file_path);
+
+  // Converts an integer into a 4 character string using the ASCII encoding.
+  // @param i the value to convert
+  // @return the String based on the number
+  // TODO(dfilimon): implement
+  static void DumpLongAsString(int32_t i, std::string* result);
+
+  // Calculate an OpenType checksum from the array.
+  // @param b the array to calculate checksum on
+  // @param offset the starting index in the array
+  // @param length the number of bytes to check; must be a multiple of 4
+  // @return checksum
+  // TODO(dfilimon): implement
+  static int64_t CheckSum(ByteArray* b, int32_t offset, int32_t length);
+
+  // Encode a single character in UTF-16.
+  // We only support the BMP for now
+  // @param encoder the encoder to use for the encoding
+  // @param uchar the Unicode character to encode
+  // @return the encoded character
+  static int32_t EncodeOneChar(UConverter* encoder, int16_t uchar);
+
+  // Get an encoder for the charset name.
+  // If the name is null or the empty string then just return null.
+  // @param charsetName the charset to get an encoder for
+  // @return an encoder or null if no encoder available for charset name
+  static UConverter* GetEncoder(const char* charsetName);
+
+ private:
+  static const char EXTENSION_SEPARATOR = '.';
+
+ public:
+  // Get the extension of a file's name.
+  // @param file the whose name to process
+  // @return string containing the extension or an empty string if
+  // there is no extension
+  static const char* Extension(const char* file_path);
+};
+}
+#endif  // SFNTLY_CPP_SRC_TEST_TEST_UTILS_H_
diff --git a/sfntly/cpp/src/test/test_utils_test.cc b/sfntly/cpp/src/test/test_utils_test.cc
new file mode 100644
index 0000000..9afc03c
--- /dev/null
+++ b/sfntly/cpp/src/test/test_utils_test.cc
@@ -0,0 +1,84 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// Must include at the first line to avoid ICU / stdint conflict.
+#include "sfntly/port/type.h"
+
+#include <stdio.h>
+#include <unicode/ucnv.h>
+#include <unicode/uchar.h>
+
+#include "gtest/gtest.h"
+#include "test/test_utils.h"
+
+namespace sfntly {
+
+// Check if proper encoding is being performed
+// Conversion is done from UTF16 to UTF8, SJIS
+bool TestEncoding() {
+  UConverter* conv = TestUtils::GetEncoder("utf8");
+  EXPECT_TRUE(conv != NULL);
+  // Ūnĭcōde̽
+  UChar from[8] = {0x016A, 0x006E, 0x012D, 0x0063, 0x014D, 0x0064, 0x0065,
+                   0x033D};
+  int32_t want[12] = {0xc5, 0xaa, 0x6e, 0xc4, 0xad, 0x63, 0xc5, 0x8d, 0x64,
+                      0x65, 0xcc, 0xbd};
+  int32_t i, j = 0;
+  for (i = 0; i < 7; ++i) {
+    int32_t encoded = TestUtils::EncodeOneChar(conv, (int16_t)from[i]);
+    for (; encoded; encoded <<= 8) {
+      byte_t b = (encoded & 0xff000000) >> 24;
+      if (!b)
+        continue;
+      EXPECT_EQ(want[j], b);
+      if (want[j++] != b) {
+        ucnv_close(conv);
+        return false;
+      }
+    }
+  }
+  ucnv_close(conv);
+  return true;
+}
+
+// Check if the proper extension is obtained
+bool TestExtension() {
+  // usual file name
+  const char *result;
+  result = TestUtils::Extension("../data/ext/tuffy.ttf");
+  EXPECT_EQ(strcmp(result, ".ttf"), 0);
+
+  // more than one 'extension'
+  result = TestUtils::Extension("tuffy.ttf.fake");
+  EXPECT_EQ(strcmp(result, ".fake"), 0);
+
+  // no extension
+  result = TestUtils::Extension("tuffy");
+  EXPECT_STREQ(result, NULL);
+
+  // bogus extension
+  result = TestUtils::Extension("tuffy.");
+  EXPECT_EQ(strcmp(result, "."), 0);
+
+  return true;
+}
+
+}  // namespace sfntly
+
+TEST(TestUtils, All) {
+  ASSERT_TRUE(sfntly::TestExtension());
+  ASSERT_TRUE(sfntly::TestEncoding());
+}
diff --git a/sfntly/cpp/src/test/test_xml_utils.cc b/sfntly/cpp/src/test/test_xml_utils.cc
new file mode 100644
index 0000000..dc65add
--- /dev/null
+++ b/sfntly/cpp/src/test/test_xml_utils.cc
@@ -0,0 +1,50 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <map>
+#include <string>
+#include "test/test_xml_utils.h"
+#include "test/tinyxml/tinyxml.h"
+
+namespace sfntly {
+void InternalGetNodesWithName(const TiXmlNode* node, const std::string& name,
+                              TiXmlNodeVector* wanted_nodes) {
+  if (node->ValueStr() == name)
+    wanted_nodes->push_back(node);
+  for (const TiXmlNode* child = node->FirstChild();
+       child != NULL; child = child->NextSibling()) {
+    InternalGetNodesWithName(child, name, wanted_nodes);
+  }
+}
+
+TiXmlNodeVector* GetNodesWithName(const TiXmlNode* node,
+                                  const std::string& name) {
+  TiXmlNodeVector* wanted_nodes = new TiXmlNodeVector;
+  InternalGetNodesWithName(node, name, wanted_nodes);
+  return wanted_nodes;
+}
+
+const TiXmlAttribute* GetAttribute(const TiXmlNode* node,
+                                   const std::string& name) {
+  for (const TiXmlAttribute* attribute = node->ToElement()->FirstAttribute();
+       attribute != NULL; attribute = attribute->Next()) {
+    if (attribute->Name() == name) {
+      return attribute;
+    }
+  }
+  return NULL;
+}
+}
diff --git a/sfntly/cpp/src/test/test_xml_utils.h b/sfntly/cpp/src/test/test_xml_utils.h
new file mode 100644
index 0000000..7a5fe49
--- /dev/null
+++ b/sfntly/cpp/src/test/test_xml_utils.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "sfntly/port/refcount.h"
+#include "test/tinyxml/tinyxml.h"
+
+#ifndef SFNTLY_CPP_SRC_TEST_TEST_XML_UTILS_H_
+#define SFNTLY_CPP_SRC_TEST_TEST_XML_UTILS_H_
+
+namespace sfntly {
+typedef std::map<std::string, std::string> AttributeMap;
+typedef std::vector<const TiXmlNode*> TiXmlNodeVector;
+
+TiXmlNodeVector* GetNodesWithName(const TiXmlNode* node,
+                                  const std::string& name);
+const TiXmlAttribute* GetAttribute(const TiXmlNode* node,
+                                   const std::string& name);
+}  // namespace sfntly
+
+#endif  // SFNTLY_CPP_SRC_TEST_TEST_XML_UTILS_H_
diff --git a/sfntly/cpp/src/test/tinyxml/tinystr.cpp b/sfntly/cpp/src/test/tinyxml/tinystr.cpp
new file mode 100644
index 0000000..0665768
--- /dev/null
+++ b/sfntly/cpp/src/test/tinyxml/tinystr.cpp
@@ -0,0 +1,111 @@
+/*
+www.sourceforge.net/projects/tinyxml
+
+This software is provided 'as-is', without any express or implied
+warranty. In no event will the authors be held liable for any
+damages arising from the use of this software.
+
+Permission is granted to anyone to use this software for any
+purpose, including commercial applications, and to alter it and
+redistribute it freely, subject to the following restrictions:
+
+1. The origin of this software must not be misrepresented; you must
+not claim that you wrote the original software. If you use this
+software in a product, an acknowledgment in the product documentation
+would be appreciated but is not required.
+
+2. Altered source versions must be plainly marked as such, and
+must not be misrepresented as being the original software.
+
+3. This notice may not be removed or altered from any source
+distribution.
+*/
+
+
+#ifndef TIXML_USE_STL
+
+#include "tinystr.h"
+
+// Error value for find primitive
+const TiXmlString::size_type TiXmlString::npos = static_cast< TiXmlString::size_type >(-1);
+
+
+// Null rep.
+TiXmlString::Rep TiXmlString::nullrep_ = { 0, 0, { '\0' } };
+
+
+void TiXmlString::reserve (size_type cap)
+{
+	if (cap > capacity())
+	{
+		TiXmlString tmp;
+		tmp.init(length(), cap);
+		memcpy(tmp.start(), data(), length());
+		swap(tmp);
+	}
+}
+
+
+TiXmlString& TiXmlString::assign(const char* str, size_type len)
+{
+	size_type cap = capacity();
+	if (len > cap || cap > 3*(len + 8))
+	{
+		TiXmlString tmp;
+		tmp.init(len);
+		memcpy(tmp.start(), str, len);
+		swap(tmp);
+	}
+	else
+	{
+		memmove(start(), str, len);
+		set_size(len);
+	}
+	return *this;
+}
+
+
+TiXmlString& TiXmlString::append(const char* str, size_type len)
+{
+	size_type newsize = length() + len;
+	if (newsize > capacity())
+	{
+		reserve (newsize + capacity());
+	}
+	memmove(finish(), str, len);
+	set_size(newsize);
+	return *this;
+}
+
+
+TiXmlString operator + (const TiXmlString & a, const TiXmlString & b)
+{
+	TiXmlString tmp;
+	tmp.reserve(a.length() + b.length());
+	tmp += a;
+	tmp += b;
+	return tmp;
+}
+
+TiXmlString operator + (const TiXmlString & a, const char* b)
+{
+	TiXmlString tmp;
+	TiXmlString::size_type b_len = static_cast<TiXmlString::size_type>( strlen(b) );
+	tmp.reserve(a.length() + b_len);
+	tmp += a;
+	tmp.append(b, b_len);
+	return tmp;
+}
+
+TiXmlString operator + (const char* a, const TiXmlString & b)
+{
+	TiXmlString tmp;
+	TiXmlString::size_type a_len = static_cast<TiXmlString::size_type>( strlen(a) );
+	tmp.reserve(a_len + b.length());
+	tmp.append(a, a_len);
+	tmp += b;
+	return tmp;
+}
+
+
+#endif	// TIXML_USE_STL
diff --git a/sfntly/cpp/src/test/tinyxml/tinystr.h b/sfntly/cpp/src/test/tinyxml/tinystr.h
new file mode 100644
index 0000000..89cca33
--- /dev/null
+++ b/sfntly/cpp/src/test/tinyxml/tinystr.h
@@ -0,0 +1,305 @@
+/*
+www.sourceforge.net/projects/tinyxml
+
+This software is provided 'as-is', without any express or implied
+warranty. In no event will the authors be held liable for any
+damages arising from the use of this software.
+
+Permission is granted to anyone to use this software for any
+purpose, including commercial applications, and to alter it and
+redistribute it freely, subject to the following restrictions:
+
+1. The origin of this software must not be misrepresented; you must
+not claim that you wrote the original software. If you use this
+software in a product, an acknowledgment in the product documentation
+would be appreciated but is not required.
+
+2. Altered source versions must be plainly marked as such, and
+must not be misrepresented as being the original software.
+
+3. This notice may not be removed or altered from any source
+distribution.
+*/
+
+
+#ifndef TIXML_USE_STL
+
+#ifndef TIXML_STRING_INCLUDED
+#define TIXML_STRING_INCLUDED
+
+#include <assert.h>
+#include <string.h>
+
+/*	The support for explicit isn't that universal, and it isn't really
+	required - it is used to check that the TiXmlString class isn't incorrectly
+	used. Be nice to old compilers and macro it here:
+*/
+#if defined(_MSC_VER) && (_MSC_VER >= 1200 )
+	// Microsoft visual studio, version 6 and higher.
+	#define TIXML_EXPLICIT explicit
+#elif defined(__GNUC__) && (__GNUC__ >= 3 )
+	// GCC version 3 and higher.s
+	#define TIXML_EXPLICIT explicit
+#else
+	#define TIXML_EXPLICIT
+#endif
+
+
+/*
+   TiXmlString is an emulation of a subset of the std::string template.
+   Its purpose is to allow compiling TinyXML on compilers with no or poor STL support.
+   Only the member functions relevant to the TinyXML project have been implemented.
+   The buffer allocation is made by a simplistic power of 2 like mechanism : if we increase
+   a string and there's no more room, we allocate a buffer twice as big as we need.
+*/
+class TiXmlString
+{
+  public :
+	// The size type used
+  	typedef size_t size_type;
+
+	// Error value for find primitive
+	static const size_type npos; // = -1;
+
+
+	// TiXmlString empty constructor
+	TiXmlString () : rep_(&nullrep_)
+	{
+	}
+
+	// TiXmlString copy constructor
+	TiXmlString ( const TiXmlString & copy) : rep_(0)
+	{
+		init(copy.length());
+		memcpy(start(), copy.data(), length());
+	}
+
+	// TiXmlString constructor, based on a string
+	TIXML_EXPLICIT TiXmlString ( const char * copy) : rep_(0)
+	{
+		init( static_cast<size_type>( strlen(copy) ));
+		memcpy(start(), copy, length());
+	}
+
+	// TiXmlString constructor, based on a string
+	TIXML_EXPLICIT TiXmlString ( const char * str, size_type len) : rep_(0)
+	{
+		init(len);
+		memcpy(start(), str, len);
+	}
+
+	// TiXmlString destructor
+	~TiXmlString ()
+	{
+		quit();
+	}
+
+	TiXmlString& operator = (const char * copy)
+	{
+		return assign( copy, (size_type)strlen(copy));
+	}
+
+	TiXmlString& operator = (const TiXmlString & copy)
+	{
+		return assign(copy.start(), copy.length());
+	}
+
+
+	// += operator. Maps to append
+	TiXmlString& operator += (const char * suffix)
+	{
+		return append(suffix, static_cast<size_type>( strlen(suffix) ));
+	}
+
+	// += operator. Maps to append
+	TiXmlString& operator += (char single)
+	{
+		return append(&single, 1);
+	}
+
+	// += operator. Maps to append
+	TiXmlString& operator += (const TiXmlString & suffix)
+	{
+		return append(suffix.data(), suffix.length());
+	}
+
+
+	// Convert a TiXmlString into a null-terminated char *
+	const char * c_str () const { return rep_->str; }
+
+	// Convert a TiXmlString into a char * (need not be null terminated).
+	const char * data () const { return rep_->str; }
+
+	// Return the length of a TiXmlString
+	size_type length () const { return rep_->size; }
+
+	// Alias for length()
+	size_type size () const { return rep_->size; }
+
+	// Checks if a TiXmlString is empty
+	bool empty () const { return rep_->size == 0; }
+
+	// Return capacity of string
+	size_type capacity () const { return rep_->capacity; }
+
+
+	// single char extraction
+	const char& at (size_type index) const
+	{
+		assert( index < length() );
+		return rep_->str[ index ];
+	}
+
+	// [] operator
+	char& operator [] (size_type index) const
+	{
+		assert( index < length() );
+		return rep_->str[ index ];
+	}
+
+	// find a char in a string. Return TiXmlString::npos if not found
+	size_type find (char lookup) const
+	{
+		return find(lookup, 0);
+	}
+
+	// find a char in a string from an offset. Return TiXmlString::npos if not found
+	size_type find (char tofind, size_type offset) const
+	{
+		if (offset >= length()) return npos;
+
+		for (const char* p = c_str() + offset; *p != '\0'; ++p)
+		{
+		   if (*p == tofind) return static_cast< size_type >( p - c_str() );
+		}
+		return npos;
+	}
+
+	void clear ()
+	{
+		//Lee:
+		//The original was just too strange, though correct:
+		//	TiXmlString().swap(*this);
+		//Instead use the quit & re-init:
+		quit();
+		init(0,0);
+	}
+
+	/*	Function to reserve a big amount of data when we know we'll need it. Be aware that this
+		function DOES NOT clear the content of the TiXmlString if any exists.
+	*/
+	void reserve (size_type cap);
+
+	TiXmlString& assign (const char* str, size_type len);
+
+	TiXmlString& append (const char* str, size_type len);
+
+	void swap (TiXmlString& other)
+	{
+		Rep* r = rep_;
+		rep_ = other.rep_;
+		other.rep_ = r;
+	}
+
+  private:
+
+	void init(size_type sz) { init(sz, sz); }
+	void set_size(size_type sz) { rep_->str[ rep_->size = sz ] = '\0'; }
+	char* start() const { return rep_->str; }
+	char* finish() const { return rep_->str + rep_->size; }
+
+	struct Rep
+	{
+		size_type size, capacity;
+		char str[1];
+	};
+
+	void init(size_type sz, size_type cap)
+	{
+		if (cap)
+		{
+			// Lee: the original form:
+			//	rep_ = static_cast<Rep*>(operator new(sizeof(Rep) + cap));
+			// doesn't work in some cases of new being overloaded. Switching
+			// to the normal allocation, although use an 'int' for systems
+			// that are overly picky about structure alignment.
+			const size_type bytesNeeded = sizeof(Rep) + cap;
+			const size_type intsNeeded = ( bytesNeeded + sizeof(int) - 1 ) / sizeof( int ); 
+			rep_ = reinterpret_cast<Rep*>( new int[ intsNeeded ] );
+
+			rep_->str[ rep_->size = sz ] = '\0';
+			rep_->capacity = cap;
+		}
+		else
+		{
+			rep_ = &nullrep_;
+		}
+	}
+
+	void quit()
+	{
+		if (rep_ != &nullrep_)
+		{
+			// The rep_ is really an array of ints. (see the allocator, above).
+			// Cast it back before delete, so the compiler won't incorrectly call destructors.
+			delete [] ( reinterpret_cast<int*>( rep_ ) );
+		}
+	}
+
+	Rep * rep_;
+	static Rep nullrep_;
+
+} ;
+
+
+inline bool operator == (const TiXmlString & a, const TiXmlString & b)
+{
+	return    ( a.length() == b.length() )				// optimization on some platforms
+	       && ( strcmp(a.c_str(), b.c_str()) == 0 );	// actual compare
+}
+inline bool operator < (const TiXmlString & a, const TiXmlString & b)
+{
+	return strcmp(a.c_str(), b.c_str()) < 0;
+}
+
+inline bool operator != (const TiXmlString & a, const TiXmlString & b) { return !(a == b); }
+inline bool operator >  (const TiXmlString & a, const TiXmlString & b) { return b < a; }
+inline bool operator <= (const TiXmlString & a, const TiXmlString & b) { return !(b < a); }
+inline bool operator >= (const TiXmlString & a, const TiXmlString & b) { return !(a < b); }
+
+inline bool operator == (const TiXmlString & a, const char* b) { return strcmp(a.c_str(), b) == 0; }
+inline bool operator == (const char* a, const TiXmlString & b) { return b == a; }
+inline bool operator != (const TiXmlString & a, const char* b) { return !(a == b); }
+inline bool operator != (const char* a, const TiXmlString & b) { return !(b == a); }
+
+TiXmlString operator + (const TiXmlString & a, const TiXmlString & b);
+TiXmlString operator + (const TiXmlString & a, const char* b);
+TiXmlString operator + (const char* a, const TiXmlString & b);
+
+
+/*
+   TiXmlOutStream is an emulation of std::ostream. It is based on TiXmlString.
+   Only the operators that we need for TinyXML have been developped.
+*/
+class TiXmlOutStream : public TiXmlString
+{
+public :
+
+	// TiXmlOutStream << operator.
+	TiXmlOutStream & operator << (const TiXmlString & in)
+	{
+		*this += in;
+		return *this;
+	}
+
+	// TiXmlOutStream << operator.
+	TiXmlOutStream & operator << (const char * in)
+	{
+		*this += in;
+		return *this;
+	}
+
+} ;
+
+#endif	// TIXML_STRING_INCLUDED
+#endif	// TIXML_USE_STL
diff --git a/sfntly/cpp/src/test/tinyxml/tinyxml.cpp b/sfntly/cpp/src/test/tinyxml/tinyxml.cpp
new file mode 100644
index 0000000..9c161df
--- /dev/null
+++ b/sfntly/cpp/src/test/tinyxml/tinyxml.cpp
@@ -0,0 +1,1886 @@
+/*
+www.sourceforge.net/projects/tinyxml
+Original code by Lee Thomason (www.grinninglizard.com)
+
+This software is provided 'as-is', without any express or implied
+warranty. In no event will the authors be held liable for any
+damages arising from the use of this software.
+
+Permission is granted to anyone to use this software for any
+purpose, including commercial applications, and to alter it and
+redistribute it freely, subject to the following restrictions:
+
+1. The origin of this software must not be misrepresented; you must
+not claim that you wrote the original software. If you use this
+software in a product, an acknowledgment in the product documentation
+would be appreciated but is not required.
+
+2. Altered source versions must be plainly marked as such, and
+must not be misrepresented as being the original software.
+
+3. This notice may not be removed or altered from any source
+distribution.
+*/
+
+#include <ctype.h>
+
+#ifdef TIXML_USE_STL
+#include <sstream>
+#include <iostream>
+#endif
+
+#include "tinyxml.h"
+
+FILE* TiXmlFOpen( const char* filename, const char* mode );
+
+bool TiXmlBase::condenseWhiteSpace = true;
+
+// Microsoft compiler security
+FILE* TiXmlFOpen( const char* filename, const char* mode )
+{
+	#if defined(_MSC_VER) && (_MSC_VER >= 1400 )
+		FILE* fp = 0;
+		errno_t err = fopen_s( &fp, filename, mode );
+		if ( !err && fp )
+			return fp;
+		return 0;
+	#else
+		return fopen( filename, mode );
+	#endif
+}
+
+void TiXmlBase::EncodeString( const TIXML_STRING& str, TIXML_STRING* outString )
+{
+	int i=0;
+
+	while( i<(int)str.length() )
+	{
+		unsigned char c = (unsigned char) str[i];
+
+		if (    c == '&' 
+		     && i < ( (int)str.length() - 2 )
+			 && str[i+1] == '#'
+			 && str[i+2] == 'x' )
+		{
+			// Hexadecimal character reference.
+			// Pass through unchanged.
+			// &#xA9;	-- copyright symbol, for example.
+			//
+			// The -1 is a bug fix from Rob Laveaux. It keeps
+			// an overflow from happening if there is no ';'.
+			// There are actually 2 ways to exit this loop -
+			// while fails (error case) and break (semicolon found).
+			// However, there is no mechanism (currently) for
+			// this function to return an error.
+			while ( i<(int)str.length()-1 )
+			{
+				outString->append( str.c_str() + i, 1 );
+				++i;
+				if ( str[i] == ';' )
+					break;
+			}
+		}
+		else if ( c == '&' )
+		{
+			outString->append( entity[0].str, entity[0].strLength );
+			++i;
+		}
+		else if ( c == '<' )
+		{
+			outString->append( entity[1].str, entity[1].strLength );
+			++i;
+		}
+		else if ( c == '>' )
+		{
+			outString->append( entity[2].str, entity[2].strLength );
+			++i;
+		}
+		else if ( c == '\"' )
+		{
+			outString->append( entity[3].str, entity[3].strLength );
+			++i;
+		}
+		else if ( c == '\'' )
+		{
+			outString->append( entity[4].str, entity[4].strLength );
+			++i;
+		}
+		else if ( c < 32 )
+		{
+			// Easy pass at non-alpha/numeric/symbol
+			// Below 32 is symbolic.
+			char buf[ 32 ];
+			
+			#if defined(TIXML_SNPRINTF)		
+				TIXML_SNPRINTF( buf, sizeof(buf), "&#x%02X;", (unsigned) ( c & 0xff ) );
+			#else
+				sprintf( buf, "&#x%02X;", (unsigned) ( c & 0xff ) );
+			#endif		
+
+			//*ME:	warning C4267: convert 'size_t' to 'int'
+			//*ME:	Int-Cast to make compiler happy ...
+			outString->append( buf, (int)strlen( buf ) );
+			++i;
+		}
+		else
+		{
+			//char realc = (char) c;
+			//outString->append( &realc, 1 );
+			*outString += (char) c;	// somewhat more efficient function call.
+			++i;
+		}
+	}
+}
+
+
+TiXmlNode::TiXmlNode( NodeType _type ) : TiXmlBase()
+{
+	parent = 0;
+	type = _type;
+	firstChild = 0;
+	lastChild = 0;
+	prev = 0;
+	next = 0;
+}
+
+
+TiXmlNode::~TiXmlNode()
+{
+	TiXmlNode* node = firstChild;
+	TiXmlNode* temp = 0;
+
+	while ( node )
+	{
+		temp = node;
+		node = node->next;
+		delete temp;
+	}	
+}
+
+
+void TiXmlNode::CopyTo( TiXmlNode* target ) const
+{
+	target->SetValue (value.c_str() );
+	target->userData = userData; 
+	target->location = location;
+}
+
+
+void TiXmlNode::Clear()
+{
+	TiXmlNode* node = firstChild;
+	TiXmlNode* temp = 0;
+
+	while ( node )
+	{
+		temp = node;
+		node = node->next;
+		delete temp;
+	}	
+
+	firstChild = 0;
+	lastChild = 0;
+}
+
+
+TiXmlNode* TiXmlNode::LinkEndChild( TiXmlNode* node )
+{
+	assert( node->parent == 0 || node->parent == this );
+	assert( node->GetDocument() == 0 || node->GetDocument() == this->GetDocument() );
+
+	if ( node->Type() == TiXmlNode::TINYXML_DOCUMENT )
+	{
+		delete node;
+		if ( GetDocument() ) 
+			GetDocument()->SetError( TIXML_ERROR_DOCUMENT_TOP_ONLY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return 0;
+	}
+
+	node->parent = this;
+
+	node->prev = lastChild;
+	node->next = 0;
+
+	if ( lastChild )
+		lastChild->next = node;
+	else
+		firstChild = node;			// it was an empty list.
+
+	lastChild = node;
+	return node;
+}
+
+
+TiXmlNode* TiXmlNode::InsertEndChild( const TiXmlNode& addThis )
+{
+	if ( addThis.Type() == TiXmlNode::TINYXML_DOCUMENT )
+	{
+		if ( GetDocument() ) 
+			GetDocument()->SetError( TIXML_ERROR_DOCUMENT_TOP_ONLY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return 0;
+	}
+	TiXmlNode* node = addThis.Clone();
+	if ( !node )
+		return 0;
+
+	return LinkEndChild( node );
+}
+
+
+TiXmlNode* TiXmlNode::InsertBeforeChild( TiXmlNode* beforeThis, const TiXmlNode& addThis )
+{	
+	if ( !beforeThis || beforeThis->parent != this ) {
+		return 0;
+	}
+	if ( addThis.Type() == TiXmlNode::TINYXML_DOCUMENT )
+	{
+		if ( GetDocument() ) 
+			GetDocument()->SetError( TIXML_ERROR_DOCUMENT_TOP_ONLY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return 0;
+	}
+
+	TiXmlNode* node = addThis.Clone();
+	if ( !node )
+		return 0;
+	node->parent = this;
+
+	node->next = beforeThis;
+	node->prev = beforeThis->prev;
+	if ( beforeThis->prev )
+	{
+		beforeThis->prev->next = node;
+	}
+	else
+	{
+		assert( firstChild == beforeThis );
+		firstChild = node;
+	}
+	beforeThis->prev = node;
+	return node;
+}
+
+
+TiXmlNode* TiXmlNode::InsertAfterChild( TiXmlNode* afterThis, const TiXmlNode& addThis )
+{
+	if ( !afterThis || afterThis->parent != this ) {
+		return 0;
+	}
+	if ( addThis.Type() == TiXmlNode::TINYXML_DOCUMENT )
+	{
+		if ( GetDocument() ) 
+			GetDocument()->SetError( TIXML_ERROR_DOCUMENT_TOP_ONLY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return 0;
+	}
+
+	TiXmlNode* node = addThis.Clone();
+	if ( !node )
+		return 0;
+	node->parent = this;
+
+	node->prev = afterThis;
+	node->next = afterThis->next;
+	if ( afterThis->next )
+	{
+		afterThis->next->prev = node;
+	}
+	else
+	{
+		assert( lastChild == afterThis );
+		lastChild = node;
+	}
+	afterThis->next = node;
+	return node;
+}
+
+
+TiXmlNode* TiXmlNode::ReplaceChild( TiXmlNode* replaceThis, const TiXmlNode& withThis )
+{
+	if ( !replaceThis )
+		return 0;
+
+	if ( replaceThis->parent != this )
+		return 0;
+
+	if ( withThis.ToDocument() ) {
+		// A document can never be a child.	Thanks to Noam.
+		TiXmlDocument* document = GetDocument();
+		if ( document ) 
+			document->SetError( TIXML_ERROR_DOCUMENT_TOP_ONLY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return 0;
+	}
+
+	TiXmlNode* node = withThis.Clone();
+	if ( !node )
+		return 0;
+
+	node->next = replaceThis->next;
+	node->prev = replaceThis->prev;
+
+	if ( replaceThis->next )
+		replaceThis->next->prev = node;
+	else
+		lastChild = node;
+
+	if ( replaceThis->prev )
+		replaceThis->prev->next = node;
+	else
+		firstChild = node;
+
+	delete replaceThis;
+	node->parent = this;
+	return node;
+}
+
+
+bool TiXmlNode::RemoveChild( TiXmlNode* removeThis )
+{
+	if ( !removeThis ) {
+		return false;
+	}
+
+	if ( removeThis->parent != this )
+	{	
+		assert( 0 );
+		return false;
+	}
+
+	if ( removeThis->next )
+		removeThis->next->prev = removeThis->prev;
+	else
+		lastChild = removeThis->prev;
+
+	if ( removeThis->prev )
+		removeThis->prev->next = removeThis->next;
+	else
+		firstChild = removeThis->next;
+
+	delete removeThis;
+	return true;
+}
+
+const TiXmlNode* TiXmlNode::FirstChild( const char * _value ) const
+{
+	const TiXmlNode* node;
+	for ( node = firstChild; node; node = node->next )
+	{
+		if ( strcmp( node->Value(), _value ) == 0 )
+			return node;
+	}
+	return 0;
+}
+
+
+const TiXmlNode* TiXmlNode::LastChild( const char * _value ) const
+{
+	const TiXmlNode* node;
+	for ( node = lastChild; node; node = node->prev )
+	{
+		if ( strcmp( node->Value(), _value ) == 0 )
+			return node;
+	}
+	return 0;
+}
+
+
+const TiXmlNode* TiXmlNode::IterateChildren( const TiXmlNode* previous ) const
+{
+	if ( !previous )
+	{
+		return FirstChild();
+	}
+	else
+	{
+		assert( previous->parent == this );
+		return previous->NextSibling();
+	}
+}
+
+
+const TiXmlNode* TiXmlNode::IterateChildren( const char * val, const TiXmlNode* previous ) const
+{
+	if ( !previous )
+	{
+		return FirstChild( val );
+	}
+	else
+	{
+		assert( previous->parent == this );
+		return previous->NextSibling( val );
+	}
+}
+
+
+const TiXmlNode* TiXmlNode::NextSibling( const char * _value ) const 
+{
+	const TiXmlNode* node;
+	for ( node = next; node; node = node->next )
+	{
+		if ( strcmp( node->Value(), _value ) == 0 )
+			return node;
+	}
+	return 0;
+}
+
+
+const TiXmlNode* TiXmlNode::PreviousSibling( const char * _value ) const
+{
+	const TiXmlNode* node;
+	for ( node = prev; node; node = node->prev )
+	{
+		if ( strcmp( node->Value(), _value ) == 0 )
+			return node;
+	}
+	return 0;
+}
+
+
+void TiXmlElement::RemoveAttribute( const char * name )
+{
+    #ifdef TIXML_USE_STL
+	TIXML_STRING str( name );
+	TiXmlAttribute* node = attributeSet.Find( str );
+	#else
+	TiXmlAttribute* node = attributeSet.Find( name );
+	#endif
+	if ( node )
+	{
+		attributeSet.Remove( node );
+		delete node;
+	}
+}
+
+const TiXmlElement* TiXmlNode::FirstChildElement() const
+{
+	const TiXmlNode* node;
+
+	for (	node = FirstChild();
+			node;
+			node = node->NextSibling() )
+	{
+		if ( node->ToElement() )
+			return node->ToElement();
+	}
+	return 0;
+}
+
+
+const TiXmlElement* TiXmlNode::FirstChildElement( const char * _value ) const
+{
+	const TiXmlNode* node;
+
+	for (	node = FirstChild( _value );
+			node;
+			node = node->NextSibling( _value ) )
+	{
+		if ( node->ToElement() )
+			return node->ToElement();
+	}
+	return 0;
+}
+
+
+const TiXmlElement* TiXmlNode::NextSiblingElement() const
+{
+	const TiXmlNode* node;
+
+	for (	node = NextSibling();
+			node;
+			node = node->NextSibling() )
+	{
+		if ( node->ToElement() )
+			return node->ToElement();
+	}
+	return 0;
+}
+
+
+const TiXmlElement* TiXmlNode::NextSiblingElement( const char * _value ) const
+{
+	const TiXmlNode* node;
+
+	for (	node = NextSibling( _value );
+			node;
+			node = node->NextSibling( _value ) )
+	{
+		if ( node->ToElement() )
+			return node->ToElement();
+	}
+	return 0;
+}
+
+
+const TiXmlDocument* TiXmlNode::GetDocument() const
+{
+	const TiXmlNode* node;
+
+	for( node = this; node; node = node->parent )
+	{
+		if ( node->ToDocument() )
+			return node->ToDocument();
+	}
+	return 0;
+}
+
+
+TiXmlElement::TiXmlElement (const char * _value)
+	: TiXmlNode( TiXmlNode::TINYXML_ELEMENT )
+{
+	firstChild = lastChild = 0;
+	value = _value;
+}
+
+
+#ifdef TIXML_USE_STL
+TiXmlElement::TiXmlElement( const std::string& _value ) 
+	: TiXmlNode( TiXmlNode::TINYXML_ELEMENT )
+{
+	firstChild = lastChild = 0;
+	value = _value;
+}
+#endif
+
+
+TiXmlElement::TiXmlElement( const TiXmlElement& copy)
+	: TiXmlNode( TiXmlNode::TINYXML_ELEMENT )
+{
+	firstChild = lastChild = 0;
+	copy.CopyTo( this );	
+}
+
+
+TiXmlElement& TiXmlElement::operator=( const TiXmlElement& base )
+{
+	ClearThis();
+	base.CopyTo( this );
+	return *this;
+}
+
+
+TiXmlElement::~TiXmlElement()
+{
+	ClearThis();
+}
+
+
+void TiXmlElement::ClearThis()
+{
+	Clear();
+	while( attributeSet.First() )
+	{
+		TiXmlAttribute* node = attributeSet.First();
+		attributeSet.Remove( node );
+		delete node;
+	}
+}
+
+
+const char* TiXmlElement::Attribute( const char* name ) const
+{
+	const TiXmlAttribute* node = attributeSet.Find( name );
+	if ( node )
+		return node->Value();
+	return 0;
+}
+
+
+#ifdef TIXML_USE_STL
+const std::string* TiXmlElement::Attribute( const std::string& name ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	if ( attrib )
+		return &attrib->ValueStr();
+	return 0;
+}
+#endif
+
+
+const char* TiXmlElement::Attribute( const char* name, int* i ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	const char* result = 0;
+
+	if ( attrib ) {
+		result = attrib->Value();
+		if ( i ) {
+			attrib->QueryIntValue( i );
+		}
+	}
+	return result;
+}
+
+
+#ifdef TIXML_USE_STL
+const std::string* TiXmlElement::Attribute( const std::string& name, int* i ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	const std::string* result = 0;
+
+	if ( attrib ) {
+		result = &attrib->ValueStr();
+		if ( i ) {
+			attrib->QueryIntValue( i );
+		}
+	}
+	return result;
+}
+#endif
+
+
+const char* TiXmlElement::Attribute( const char* name, double* d ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	const char* result = 0;
+
+	if ( attrib ) {
+		result = attrib->Value();
+		if ( d ) {
+			attrib->QueryDoubleValue( d );
+		}
+	}
+	return result;
+}
+
+
+#ifdef TIXML_USE_STL
+const std::string* TiXmlElement::Attribute( const std::string& name, double* d ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	const std::string* result = 0;
+
+	if ( attrib ) {
+		result = &attrib->ValueStr();
+		if ( d ) {
+			attrib->QueryDoubleValue( d );
+		}
+	}
+	return result;
+}
+#endif
+
+
+int TiXmlElement::QueryIntAttribute( const char* name, int* ival ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	if ( !attrib )
+		return TIXML_NO_ATTRIBUTE;
+	return attrib->QueryIntValue( ival );
+}
+
+
+int TiXmlElement::QueryUnsignedAttribute( const char* name, unsigned* value ) const
+{
+	const TiXmlAttribute* node = attributeSet.Find( name );
+	if ( !node )
+		return TIXML_NO_ATTRIBUTE;
+
+	int ival = 0;
+	int result = node->QueryIntValue( &ival );
+	*value = (unsigned)ival;
+	return result;
+}
+
+
+int TiXmlElement::QueryBoolAttribute( const char* name, bool* bval ) const
+{
+	const TiXmlAttribute* node = attributeSet.Find( name );
+	if ( !node )
+		return TIXML_NO_ATTRIBUTE;
+	
+	int result = TIXML_WRONG_TYPE;
+	if (    StringEqual( node->Value(), "true", true, TIXML_ENCODING_UNKNOWN ) 
+		 || StringEqual( node->Value(), "yes", true, TIXML_ENCODING_UNKNOWN ) 
+		 || StringEqual( node->Value(), "1", true, TIXML_ENCODING_UNKNOWN ) ) 
+	{
+		*bval = true;
+		result = TIXML_SUCCESS;
+	}
+	else if (    StringEqual( node->Value(), "false", true, TIXML_ENCODING_UNKNOWN ) 
+			  || StringEqual( node->Value(), "no", true, TIXML_ENCODING_UNKNOWN ) 
+			  || StringEqual( node->Value(), "0", true, TIXML_ENCODING_UNKNOWN ) ) 
+	{
+		*bval = false;
+		result = TIXML_SUCCESS;
+	}
+	return result;
+}
+
+
+
+#ifdef TIXML_USE_STL
+int TiXmlElement::QueryIntAttribute( const std::string& name, int* ival ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	if ( !attrib )
+		return TIXML_NO_ATTRIBUTE;
+	return attrib->QueryIntValue( ival );
+}
+#endif
+
+
+int TiXmlElement::QueryDoubleAttribute( const char* name, double* dval ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	if ( !attrib )
+		return TIXML_NO_ATTRIBUTE;
+	return attrib->QueryDoubleValue( dval );
+}
+
+
+#ifdef TIXML_USE_STL
+int TiXmlElement::QueryDoubleAttribute( const std::string& name, double* dval ) const
+{
+	const TiXmlAttribute* attrib = attributeSet.Find( name );
+	if ( !attrib )
+		return TIXML_NO_ATTRIBUTE;
+	return attrib->QueryDoubleValue( dval );
+}
+#endif
+
+
+void TiXmlElement::SetAttribute( const char * name, int val )
+{	
+	TiXmlAttribute* attrib = attributeSet.FindOrCreate( name );
+	if ( attrib ) {
+		attrib->SetIntValue( val );
+	}
+}
+
+
+#ifdef TIXML_USE_STL
+void TiXmlElement::SetAttribute( const std::string& name, int val )
+{	
+	TiXmlAttribute* attrib = attributeSet.FindOrCreate( name );
+	if ( attrib ) {
+		attrib->SetIntValue( val );
+	}
+}
+#endif
+
+
+void TiXmlElement::SetDoubleAttribute( const char * name, double val )
+{	
+	TiXmlAttribute* attrib = attributeSet.FindOrCreate( name );
+	if ( attrib ) {
+		attrib->SetDoubleValue( val );
+	}
+}
+
+
+#ifdef TIXML_USE_STL
+void TiXmlElement::SetDoubleAttribute( const std::string& name, double val )
+{	
+	TiXmlAttribute* attrib = attributeSet.FindOrCreate( name );
+	if ( attrib ) {
+		attrib->SetDoubleValue( val );
+	}
+}
+#endif 
+
+
+void TiXmlElement::SetAttribute( const char * cname, const char * cvalue )
+{
+	TiXmlAttribute* attrib = attributeSet.FindOrCreate( cname );
+	if ( attrib ) {
+		attrib->SetValue( cvalue );
+	}
+}
+
+
+#ifdef TIXML_USE_STL
+void TiXmlElement::SetAttribute( const std::string& _name, const std::string& _value )
+{
+	TiXmlAttribute* attrib = attributeSet.FindOrCreate( _name );
+	if ( attrib ) {
+		attrib->SetValue( _value );
+	}
+}
+#endif
+
+
+void TiXmlElement::Print( FILE* cfile, int depth ) const
+{
+	int i;
+	assert( cfile );
+	for ( i=0; i<depth; i++ ) {
+		fprintf( cfile, "    " );
+	}
+
+	fprintf( cfile, "<%s", value.c_str() );
+
+	const TiXmlAttribute* attrib;
+	for ( attrib = attributeSet.First(); attrib; attrib = attrib->Next() )
+	{
+		fprintf( cfile, " " );
+		attrib->Print( cfile, depth );
+	}
+
+	// There are 3 different formatting approaches:
+	// 1) An element without children is printed as a <foo /> node
+	// 2) An element with only a text child is printed as <foo> text </foo>
+	// 3) An element with children is printed on multiple lines.
+	TiXmlNode* node;
+	if ( !firstChild )
+	{
+		fprintf( cfile, " />" );
+	}
+	else if ( firstChild == lastChild && firstChild->ToText() )
+	{
+		fprintf( cfile, ">" );
+		firstChild->Print( cfile, depth + 1 );
+		fprintf( cfile, "</%s>", value.c_str() );
+	}
+	else
+	{
+		fprintf( cfile, ">" );
+
+		for ( node = firstChild; node; node=node->NextSibling() )
+		{
+			if ( !node->ToText() )
+			{
+				fprintf( cfile, "\n" );
+			}
+			node->Print( cfile, depth+1 );
+		}
+		fprintf( cfile, "\n" );
+		for( i=0; i<depth; ++i ) {
+			fprintf( cfile, "    " );
+		}
+		fprintf( cfile, "</%s>", value.c_str() );
+	}
+}
+
+
+void TiXmlElement::CopyTo( TiXmlElement* target ) const
+{
+	// superclass:
+	TiXmlNode::CopyTo( target );
+
+	// Element class: 
+	// Clone the attributes, then clone the children.
+	const TiXmlAttribute* attribute = 0;
+	for(	attribute = attributeSet.First();
+	attribute;
+	attribute = attribute->Next() )
+	{
+		target->SetAttribute( attribute->Name(), attribute->Value() );
+	}
+
+	TiXmlNode* node = 0;
+	for ( node = firstChild; node; node = node->NextSibling() )
+	{
+		target->LinkEndChild( node->Clone() );
+	}
+}
+
+bool TiXmlElement::Accept( TiXmlVisitor* visitor ) const
+{
+	if ( visitor->VisitEnter( *this, attributeSet.First() ) ) 
+	{
+		for ( const TiXmlNode* node=FirstChild(); node; node=node->NextSibling() )
+		{
+			if ( !node->Accept( visitor ) )
+				break;
+		}
+	}
+	return visitor->VisitExit( *this );
+}
+
+
+TiXmlNode* TiXmlElement::Clone() const
+{
+	TiXmlElement* clone = new TiXmlElement( Value() );
+	if ( !clone )
+		return 0;
+
+	CopyTo( clone );
+	return clone;
+}
+
+
+const char* TiXmlElement::GetText() const
+{
+	const TiXmlNode* child = this->FirstChild();
+	if ( child ) {
+		const TiXmlText* childText = child->ToText();
+		if ( childText ) {
+			return childText->Value();
+		}
+	}
+	return 0;
+}
+
+
+TiXmlDocument::TiXmlDocument() : TiXmlNode( TiXmlNode::TINYXML_DOCUMENT )
+{
+	tabsize = 4;
+	useMicrosoftBOM = false;
+	ClearError();
+}
+
+TiXmlDocument::TiXmlDocument( const char * documentName ) : TiXmlNode( TiXmlNode::TINYXML_DOCUMENT )
+{
+	tabsize = 4;
+	useMicrosoftBOM = false;
+	value = documentName;
+	ClearError();
+}
+
+
+#ifdef TIXML_USE_STL
+TiXmlDocument::TiXmlDocument( const std::string& documentName ) : TiXmlNode( TiXmlNode::TINYXML_DOCUMENT )
+{
+	tabsize = 4;
+	useMicrosoftBOM = false;
+    value = documentName;
+	ClearError();
+}
+#endif
+
+
+TiXmlDocument::TiXmlDocument( const TiXmlDocument& copy ) : TiXmlNode( TiXmlNode::TINYXML_DOCUMENT )
+{
+	copy.CopyTo( this );
+}
+
+
+TiXmlDocument& TiXmlDocument::operator=( const TiXmlDocument& copy )
+{
+	Clear();
+	copy.CopyTo( this );
+	return *this;
+}
+
+
+bool TiXmlDocument::LoadFile( TiXmlEncoding encoding )
+{
+	return LoadFile( Value(), encoding );
+}
+
+
+bool TiXmlDocument::SaveFile() const
+{
+	return SaveFile( Value() );
+}
+
+bool TiXmlDocument::LoadFile( const char* _filename, TiXmlEncoding encoding )
+{
+	TIXML_STRING filename( _filename );
+	value = filename;
+
+	// reading in binary mode so that tinyxml can normalize the EOL
+	FILE* file = TiXmlFOpen( value.c_str (), "rb" );	
+
+	if ( file )
+	{
+		bool result = LoadFile( file, encoding );
+		fclose( file );
+		return result;
+	}
+	else
+	{
+		SetError( TIXML_ERROR_OPENING_FILE, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return false;
+	}
+}
+
+bool TiXmlDocument::LoadFile( FILE* file, TiXmlEncoding encoding )
+{
+	if ( !file ) 
+	{
+		SetError( TIXML_ERROR_OPENING_FILE, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return false;
+	}
+
+	// Delete the existing data:
+	Clear();
+	location.Clear();
+
+	// Get the file size, so we can pre-allocate the string. HUGE speed impact.
+	long length = 0;
+	fseek( file, 0, SEEK_END );
+	length = ftell( file );
+	fseek( file, 0, SEEK_SET );
+
+	// Strange case, but good to handle up front.
+	if ( length <= 0 )
+	{
+		SetError( TIXML_ERROR_DOCUMENT_EMPTY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return false;
+	}
+
+	// Subtle bug here. TinyXml did use fgets. But from the XML spec:
+	// 2.11 End-of-Line Handling
+	// <snip>
+	// <quote>
+	// ...the XML processor MUST behave as if it normalized all line breaks in external 
+	// parsed entities (including the document entity) on input, before parsing, by translating 
+	// both the two-character sequence #xD #xA and any #xD that is not followed by #xA to 
+	// a single #xA character.
+	// </quote>
+	//
+	// It is not clear fgets does that, and certainly isn't clear it works cross platform. 
+	// Generally, you expect fgets to translate from the convention of the OS to the c/unix
+	// convention, and not work generally.
+
+	/*
+	while( fgets( buf, sizeof(buf), file ) )
+	{
+		data += buf;
+	}
+	*/
+
+	char* buf = new char[ length+1 ];
+	buf[0] = 0;
+
+	if ( fread( buf, length, 1, file ) != 1 ) {
+		delete [] buf;
+		SetError( TIXML_ERROR_OPENING_FILE, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return false;
+	}
+
+	// Process the buffer in place to normalize new lines. (See comment above.)
+	// Copies from the 'p' to 'q' pointer, where p can advance faster if
+	// a newline-carriage return is hit.
+	//
+	// Wikipedia:
+	// Systems based on ASCII or a compatible character set use either LF  (Line feed, '\n', 0x0A, 10 in decimal) or 
+	// CR (Carriage return, '\r', 0x0D, 13 in decimal) individually, or CR followed by LF (CR+LF, 0x0D 0x0A)...
+	//		* LF:    Multics, Unix and Unix-like systems (GNU/Linux, AIX, Xenix, Mac OS X, FreeBSD, etc.), BeOS, Amiga, RISC OS, and others
+    //		* CR+LF: DEC RT-11 and most other early non-Unix, non-IBM OSes, CP/M, MP/M, DOS, OS/2, Microsoft Windows, Symbian OS
+    //		* CR:    Commodore 8-bit machines, Apple II family, Mac OS up to version 9 and OS-9
+
+	const char* p = buf;	// the read head
+	char* q = buf;			// the write head
+	const char CR = 0x0d;
+	const char LF = 0x0a;
+
+	buf[length] = 0;
+	while( *p ) {
+		assert( p < (buf+length) );
+		assert( q <= (buf+length) );
+		assert( q <= p );
+
+		if ( *p == CR ) {
+			*q++ = LF;
+			p++;
+			if ( *p == LF ) {		// check for CR+LF (and skip LF)
+				p++;
+			}
+		}
+		else {
+			*q++ = *p++;
+		}
+	}
+	assert( q <= (buf+length) );
+	*q = 0;
+
+	Parse( buf, 0, encoding );
+
+	delete [] buf;
+	return !Error();
+}
+
+
+bool TiXmlDocument::SaveFile( const char * filename ) const
+{
+	// The old c stuff lives on...
+	FILE* fp = TiXmlFOpen( filename, "w" );
+	if ( fp )
+	{
+		bool result = SaveFile( fp );
+		fclose( fp );
+		return result;
+	}
+	return false;
+}
+
+
+bool TiXmlDocument::SaveFile( FILE* fp ) const
+{
+	if ( useMicrosoftBOM ) 
+	{
+		const unsigned char TIXML_UTF_LEAD_0 = 0xefU;
+		const unsigned char TIXML_UTF_LEAD_1 = 0xbbU;
+		const unsigned char TIXML_UTF_LEAD_2 = 0xbfU;
+
+		fputc( TIXML_UTF_LEAD_0, fp );
+		fputc( TIXML_UTF_LEAD_1, fp );
+		fputc( TIXML_UTF_LEAD_2, fp );
+	}
+	Print( fp, 0 );
+	return (ferror(fp) == 0);
+}
+
+
+void TiXmlDocument::CopyTo( TiXmlDocument* target ) const
+{
+	TiXmlNode::CopyTo( target );
+
+	target->error = error;
+	target->errorId = errorId;
+	target->errorDesc = errorDesc;
+	target->tabsize = tabsize;
+	target->errorLocation = errorLocation;
+	target->useMicrosoftBOM = useMicrosoftBOM;
+
+	TiXmlNode* node = 0;
+	for ( node = firstChild; node; node = node->NextSibling() )
+	{
+		target->LinkEndChild( node->Clone() );
+	}	
+}
+
+
+TiXmlNode* TiXmlDocument::Clone() const
+{
+	TiXmlDocument* clone = new TiXmlDocument();
+	if ( !clone )
+		return 0;
+
+	CopyTo( clone );
+	return clone;
+}
+
+
+void TiXmlDocument::Print( FILE* cfile, int depth ) const
+{
+	assert( cfile );
+	for ( const TiXmlNode* node=FirstChild(); node; node=node->NextSibling() )
+	{
+		node->Print( cfile, depth );
+		fprintf( cfile, "\n" );
+	}
+}
+
+
+bool TiXmlDocument::Accept( TiXmlVisitor* visitor ) const
+{
+	if ( visitor->VisitEnter( *this ) )
+	{
+		for ( const TiXmlNode* node=FirstChild(); node; node=node->NextSibling() )
+		{
+			if ( !node->Accept( visitor ) )
+				break;
+		}
+	}
+	return visitor->VisitExit( *this );
+}
+
+
+const TiXmlAttribute* TiXmlAttribute::Next() const
+{
+	// We are using knowledge of the sentinel. The sentinel
+	// have a value or name.
+	if ( next->value.empty() && next->name.empty() )
+		return 0;
+	return next;
+}
+
+/*
+TiXmlAttribute* TiXmlAttribute::Next()
+{
+	// We are using knowledge of the sentinel. The sentinel
+	// have a value or name.
+	if ( next->value.empty() && next->name.empty() )
+		return 0;
+	return next;
+}
+*/
+
+const TiXmlAttribute* TiXmlAttribute::Previous() const
+{
+	// We are using knowledge of the sentinel. The sentinel
+	// have a value or name.
+	if ( prev->value.empty() && prev->name.empty() )
+		return 0;
+	return prev;
+}
+
+/*
+TiXmlAttribute* TiXmlAttribute::Previous()
+{
+	// We are using knowledge of the sentinel. The sentinel
+	// have a value or name.
+	if ( prev->value.empty() && prev->name.empty() )
+		return 0;
+	return prev;
+}
+*/
+
+void TiXmlAttribute::Print( FILE* cfile, int /*depth*/, TIXML_STRING* str ) const
+{
+	TIXML_STRING n, v;
+
+	EncodeString( name, &n );
+	EncodeString( value, &v );
+
+	if (value.find ('\"') == TIXML_STRING::npos) {
+		if ( cfile ) {
+			fprintf (cfile, "%s=\"%s\"", n.c_str(), v.c_str() );
+		}
+		if ( str ) {
+			(*str) += n; (*str) += "=\""; (*str) += v; (*str) += "\"";
+		}
+	}
+	else {
+		if ( cfile ) {
+			fprintf (cfile, "%s='%s'", n.c_str(), v.c_str() );
+		}
+		if ( str ) {
+			(*str) += n; (*str) += "='"; (*str) += v; (*str) += "'";
+		}
+	}
+}
+
+
+int TiXmlAttribute::QueryIntValue( int* ival ) const
+{
+	if ( TIXML_SSCANF( value.c_str(), "%d", ival ) == 1 )
+		return TIXML_SUCCESS;
+	return TIXML_WRONG_TYPE;
+}
+
+int TiXmlAttribute::QueryDoubleValue( double* dval ) const
+{
+	if ( TIXML_SSCANF( value.c_str(), "%lf", dval ) == 1 )
+		return TIXML_SUCCESS;
+	return TIXML_WRONG_TYPE;
+}
+
+void TiXmlAttribute::SetIntValue( int _value )
+{
+	char buf [64];
+	#if defined(TIXML_SNPRINTF)		
+		TIXML_SNPRINTF(buf, sizeof(buf), "%d", _value);
+	#else
+		sprintf (buf, "%d", _value);
+	#endif
+	SetValue (buf);
+}
+
+void TiXmlAttribute::SetDoubleValue( double _value )
+{
+	char buf [256];
+	#if defined(TIXML_SNPRINTF)		
+		TIXML_SNPRINTF( buf, sizeof(buf), "%g", _value);
+	#else
+		sprintf (buf, "%g", _value);
+	#endif
+	SetValue (buf);
+}
+
+int TiXmlAttribute::IntValue() const
+{
+	return atoi (value.c_str ());
+}
+
+double  TiXmlAttribute::DoubleValue() const
+{
+	return atof (value.c_str ());
+}
+
+
+TiXmlComment::TiXmlComment( const TiXmlComment& copy ) : TiXmlNode( TiXmlNode::TINYXML_COMMENT )
+{
+	copy.CopyTo( this );
+}
+
+
+TiXmlComment& TiXmlComment::operator=( const TiXmlComment& base )
+{
+	Clear();
+	base.CopyTo( this );
+	return *this;
+}
+
+
+void TiXmlComment::Print( FILE* cfile, int depth ) const
+{
+	assert( cfile );
+	for ( int i=0; i<depth; i++ )
+	{
+		fprintf( cfile,  "    " );
+	}
+	fprintf( cfile, "<!--%s-->", value.c_str() );
+}
+
+
+void TiXmlComment::CopyTo( TiXmlComment* target ) const
+{
+	TiXmlNode::CopyTo( target );
+}
+
+
+bool TiXmlComment::Accept( TiXmlVisitor* visitor ) const
+{
+	return visitor->Visit( *this );
+}
+
+
+TiXmlNode* TiXmlComment::Clone() const
+{
+	TiXmlComment* clone = new TiXmlComment();
+
+	if ( !clone )
+		return 0;
+
+	CopyTo( clone );
+	return clone;
+}
+
+
+void TiXmlText::Print( FILE* cfile, int depth ) const
+{
+	assert( cfile );
+	if ( cdata )
+	{
+		int i;
+		fprintf( cfile, "\n" );
+		for ( i=0; i<depth; i++ ) {
+			fprintf( cfile, "    " );
+		}
+		fprintf( cfile, "<![CDATA[%s]]>\n", value.c_str() );	// unformatted output
+	}
+	else
+	{
+		TIXML_STRING buffer;
+		EncodeString( value, &buffer );
+		fprintf( cfile, "%s", buffer.c_str() );
+	}
+}
+
+
+void TiXmlText::CopyTo( TiXmlText* target ) const
+{
+	TiXmlNode::CopyTo( target );
+	target->cdata = cdata;
+}
+
+
+bool TiXmlText::Accept( TiXmlVisitor* visitor ) const
+{
+	return visitor->Visit( *this );
+}
+
+
+TiXmlNode* TiXmlText::Clone() const
+{	
+	TiXmlText* clone = 0;
+	clone = new TiXmlText( "" );
+
+	if ( !clone )
+		return 0;
+
+	CopyTo( clone );
+	return clone;
+}
+
+
+TiXmlDeclaration::TiXmlDeclaration( const char * _version,
+									const char * _encoding,
+									const char * _standalone )
+	: TiXmlNode( TiXmlNode::TINYXML_DECLARATION )
+{
+	version = _version;
+	encoding = _encoding;
+	standalone = _standalone;
+}
+
+
+#ifdef TIXML_USE_STL
+TiXmlDeclaration::TiXmlDeclaration(	const std::string& _version,
+									const std::string& _encoding,
+									const std::string& _standalone )
+	: TiXmlNode( TiXmlNode::TINYXML_DECLARATION )
+{
+	version = _version;
+	encoding = _encoding;
+	standalone = _standalone;
+}
+#endif
+
+
+TiXmlDeclaration::TiXmlDeclaration( const TiXmlDeclaration& copy )
+	: TiXmlNode( TiXmlNode::TINYXML_DECLARATION )
+{
+	copy.CopyTo( this );	
+}
+
+
+TiXmlDeclaration& TiXmlDeclaration::operator=( const TiXmlDeclaration& copy )
+{
+	Clear();
+	copy.CopyTo( this );
+	return *this;
+}
+
+
+void TiXmlDeclaration::Print( FILE* cfile, int /*depth*/, TIXML_STRING* str ) const
+{
+	if ( cfile ) fprintf( cfile, "<?xml " );
+	if ( str )	 (*str) += "<?xml ";
+
+	if ( !version.empty() ) {
+		if ( cfile ) fprintf (cfile, "version=\"%s\" ", version.c_str ());
+		if ( str ) { (*str) += "version=\""; (*str) += version; (*str) += "\" "; }
+	}
+	if ( !encoding.empty() ) {
+		if ( cfile ) fprintf (cfile, "encoding=\"%s\" ", encoding.c_str ());
+		if ( str ) { (*str) += "encoding=\""; (*str) += encoding; (*str) += "\" "; }
+	}
+	if ( !standalone.empty() ) {
+		if ( cfile ) fprintf (cfile, "standalone=\"%s\" ", standalone.c_str ());
+		if ( str ) { (*str) += "standalone=\""; (*str) += standalone; (*str) += "\" "; }
+	}
+	if ( cfile ) fprintf( cfile, "?>" );
+	if ( str )	 (*str) += "?>";
+}
+
+
+void TiXmlDeclaration::CopyTo( TiXmlDeclaration* target ) const
+{
+	TiXmlNode::CopyTo( target );
+
+	target->version = version;
+	target->encoding = encoding;
+	target->standalone = standalone;
+}
+
+
+bool TiXmlDeclaration::Accept( TiXmlVisitor* visitor ) const
+{
+	return visitor->Visit( *this );
+}
+
+
+TiXmlNode* TiXmlDeclaration::Clone() const
+{	
+	TiXmlDeclaration* clone = new TiXmlDeclaration();
+
+	if ( !clone )
+		return 0;
+
+	CopyTo( clone );
+	return clone;
+}
+
+
+void TiXmlUnknown::Print( FILE* cfile, int depth ) const
+{
+	for ( int i=0; i<depth; i++ )
+		fprintf( cfile, "    " );
+	fprintf( cfile, "<%s>", value.c_str() );
+}
+
+
+void TiXmlUnknown::CopyTo( TiXmlUnknown* target ) const
+{
+	TiXmlNode::CopyTo( target );
+}
+
+
+bool TiXmlUnknown::Accept( TiXmlVisitor* visitor ) const
+{
+	return visitor->Visit( *this );
+}
+
+
+TiXmlNode* TiXmlUnknown::Clone() const
+{
+	TiXmlUnknown* clone = new TiXmlUnknown();
+
+	if ( !clone )
+		return 0;
+
+	CopyTo( clone );
+	return clone;
+}
+
+
+TiXmlAttributeSet::TiXmlAttributeSet()
+{
+	sentinel.next = &sentinel;
+	sentinel.prev = &sentinel;
+}
+
+
+TiXmlAttributeSet::~TiXmlAttributeSet()
+{
+	assert( sentinel.next == &sentinel );
+	assert( sentinel.prev == &sentinel );
+}
+
+
+void TiXmlAttributeSet::Add( TiXmlAttribute* addMe )
+{
+    #ifdef TIXML_USE_STL
+	assert( !Find( TIXML_STRING( addMe->Name() ) ) );	// Shouldn't be multiply adding to the set.
+	#else
+	assert( !Find( addMe->Name() ) );	// Shouldn't be multiply adding to the set.
+	#endif
+
+	addMe->next = &sentinel;
+	addMe->prev = sentinel.prev;
+
+	sentinel.prev->next = addMe;
+	sentinel.prev      = addMe;
+}
+
+void TiXmlAttributeSet::Remove( TiXmlAttribute* removeMe )
+{
+	TiXmlAttribute* node;
+
+	for( node = sentinel.next; node != &sentinel; node = node->next )
+	{
+		if ( node == removeMe )
+		{
+			node->prev->next = node->next;
+			node->next->prev = node->prev;
+			node->next = 0;
+			node->prev = 0;
+			return;
+		}
+	}
+	assert( 0 );		// we tried to remove a non-linked attribute.
+}
+
+
+#ifdef TIXML_USE_STL
+TiXmlAttribute* TiXmlAttributeSet::Find( const std::string& name ) const
+{
+	for( TiXmlAttribute* node = sentinel.next; node != &sentinel; node = node->next )
+	{
+		if ( node->name == name )
+			return node;
+	}
+	return 0;
+}
+
+TiXmlAttribute* TiXmlAttributeSet::FindOrCreate( const std::string& _name )
+{
+	TiXmlAttribute* attrib = Find( _name );
+	if ( !attrib ) {
+		attrib = new TiXmlAttribute();
+		Add( attrib );
+		attrib->SetName( _name );
+	}
+	return attrib;
+}
+#endif
+
+
+TiXmlAttribute* TiXmlAttributeSet::Find( const char* name ) const
+{
+	for( TiXmlAttribute* node = sentinel.next; node != &sentinel; node = node->next )
+	{
+		if ( strcmp( node->name.c_str(), name ) == 0 )
+			return node;
+	}
+	return 0;
+}
+
+
+TiXmlAttribute* TiXmlAttributeSet::FindOrCreate( const char* _name )
+{
+	TiXmlAttribute* attrib = Find( _name );
+	if ( !attrib ) {
+		attrib = new TiXmlAttribute();
+		Add( attrib );
+		attrib->SetName( _name );
+	}
+	return attrib;
+}
+
+
+#ifdef TIXML_USE_STL	
+std::istream& operator>> (std::istream & in, TiXmlNode & base)
+{
+	TIXML_STRING tag;
+	tag.reserve( 8 * 1000 );
+	base.StreamIn( &in, &tag );
+
+	base.Parse( tag.c_str(), 0, TIXML_DEFAULT_ENCODING );
+	return in;
+}
+#endif
+
+
+#ifdef TIXML_USE_STL	
+std::ostream& operator<< (std::ostream & out, const TiXmlNode & base)
+{
+	TiXmlPrinter printer;
+	printer.SetStreamPrinting();
+	base.Accept( &printer );
+	out << printer.Str();
+
+	return out;
+}
+
+
+std::string& operator<< (std::string& out, const TiXmlNode& base )
+{
+	TiXmlPrinter printer;
+	printer.SetStreamPrinting();
+	base.Accept( &printer );
+	out.append( printer.Str() );
+
+	return out;
+}
+#endif
+
+
+TiXmlHandle TiXmlHandle::FirstChild() const
+{
+	if ( node )
+	{
+		TiXmlNode* child = node->FirstChild();
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+TiXmlHandle TiXmlHandle::FirstChild( const char * value ) const
+{
+	if ( node )
+	{
+		TiXmlNode* child = node->FirstChild( value );
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+TiXmlHandle TiXmlHandle::FirstChildElement() const
+{
+	if ( node )
+	{
+		TiXmlElement* child = node->FirstChildElement();
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+TiXmlHandle TiXmlHandle::FirstChildElement( const char * value ) const
+{
+	if ( node )
+	{
+		TiXmlElement* child = node->FirstChildElement( value );
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+TiXmlHandle TiXmlHandle::Child( int count ) const
+{
+	if ( node )
+	{
+		int i;
+		TiXmlNode* child = node->FirstChild();
+		for (	i=0;
+				child && i<count;
+				child = child->NextSibling(), ++i )
+		{
+			// nothing
+		}
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+TiXmlHandle TiXmlHandle::Child( const char* value, int count ) const
+{
+	if ( node )
+	{
+		int i;
+		TiXmlNode* child = node->FirstChild( value );
+		for (	i=0;
+				child && i<count;
+				child = child->NextSibling( value ), ++i )
+		{
+			// nothing
+		}
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+TiXmlHandle TiXmlHandle::ChildElement( int count ) const
+{
+	if ( node )
+	{
+		int i;
+		TiXmlElement* child = node->FirstChildElement();
+		for (	i=0;
+				child && i<count;
+				child = child->NextSiblingElement(), ++i )
+		{
+			// nothing
+		}
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+TiXmlHandle TiXmlHandle::ChildElement( const char* value, int count ) const
+{
+	if ( node )
+	{
+		int i;
+		TiXmlElement* child = node->FirstChildElement( value );
+		for (	i=0;
+				child && i<count;
+				child = child->NextSiblingElement( value ), ++i )
+		{
+			// nothing
+		}
+		if ( child )
+			return TiXmlHandle( child );
+	}
+	return TiXmlHandle( 0 );
+}
+
+
+bool TiXmlPrinter::VisitEnter( const TiXmlDocument& )
+{
+	return true;
+}
+
+bool TiXmlPrinter::VisitExit( const TiXmlDocument& )
+{
+	return true;
+}
+
+bool TiXmlPrinter::VisitEnter( const TiXmlElement& element, const TiXmlAttribute* firstAttribute )
+{
+	DoIndent();
+	buffer += "<";
+	buffer += element.Value();
+
+	for( const TiXmlAttribute* attrib = firstAttribute; attrib; attrib = attrib->Next() )
+	{
+		buffer += " ";
+		attrib->Print( 0, 0, &buffer );
+	}
+
+	if ( !element.FirstChild() ) 
+	{
+		buffer += " />";
+		DoLineBreak();
+	}
+	else 
+	{
+		buffer += ">";
+		if (    element.FirstChild()->ToText()
+			  && element.LastChild() == element.FirstChild()
+			  && element.FirstChild()->ToText()->CDATA() == false )
+		{
+			simpleTextPrint = true;
+			// no DoLineBreak()!
+		}
+		else
+		{
+			DoLineBreak();
+		}
+	}
+	++depth;	
+	return true;
+}
+
+
+bool TiXmlPrinter::VisitExit( const TiXmlElement& element )
+{
+	--depth;
+	if ( !element.FirstChild() ) 
+	{
+		// nothing.
+	}
+	else 
+	{
+		if ( simpleTextPrint )
+		{
+			simpleTextPrint = false;
+		}
+		else
+		{
+			DoIndent();
+		}
+		buffer += "</";
+		buffer += element.Value();
+		buffer += ">";
+		DoLineBreak();
+	}
+	return true;
+}
+
+
+bool TiXmlPrinter::Visit( const TiXmlText& text )
+{
+	if ( text.CDATA() )
+	{
+		DoIndent();
+		buffer += "<![CDATA[";
+		buffer += text.Value();
+		buffer += "]]>";
+		DoLineBreak();
+	}
+	else if ( simpleTextPrint )
+	{
+		TIXML_STRING str;
+		TiXmlBase::EncodeString( text.ValueTStr(), &str );
+		buffer += str;
+	}
+	else
+	{
+		DoIndent();
+		TIXML_STRING str;
+		TiXmlBase::EncodeString( text.ValueTStr(), &str );
+		buffer += str;
+		DoLineBreak();
+	}
+	return true;
+}
+
+
+bool TiXmlPrinter::Visit( const TiXmlDeclaration& declaration )
+{
+	DoIndent();
+	declaration.Print( 0, 0, &buffer );
+	DoLineBreak();
+	return true;
+}
+
+
+bool TiXmlPrinter::Visit( const TiXmlComment& comment )
+{
+	DoIndent();
+	buffer += "<!--";
+	buffer += comment.Value();
+	buffer += "-->";
+	DoLineBreak();
+	return true;
+}
+
+
+bool TiXmlPrinter::Visit( const TiXmlUnknown& unknown )
+{
+	DoIndent();
+	buffer += "<";
+	buffer += unknown.Value();
+	buffer += ">";
+	DoLineBreak();
+	return true;
+}
+
diff --git a/sfntly/cpp/src/test/tinyxml/tinyxml.h b/sfntly/cpp/src/test/tinyxml/tinyxml.h
new file mode 100644
index 0000000..a3589e5
--- /dev/null
+++ b/sfntly/cpp/src/test/tinyxml/tinyxml.h
@@ -0,0 +1,1805 @@
+/*
+www.sourceforge.net/projects/tinyxml
+Original code by Lee Thomason (www.grinninglizard.com)
+
+This software is provided 'as-is', without any express or implied
+warranty. In no event will the authors be held liable for any
+damages arising from the use of this software.
+
+Permission is granted to anyone to use this software for any
+purpose, including commercial applications, and to alter it and
+redistribute it freely, subject to the following restrictions:
+
+1. The origin of this software must not be misrepresented; you must
+not claim that you wrote the original software. If you use this
+software in a product, an acknowledgment in the product documentation
+would be appreciated but is not required.
+
+2. Altered source versions must be plainly marked as such, and
+must not be misrepresented as being the original software.
+
+3. This notice may not be removed or altered from any source
+distribution.
+*/
+
+
+#ifndef TINYXML_INCLUDED
+#define TINYXML_INCLUDED
+
+#ifdef _MSC_VER
+#pragma warning( push )
+#pragma warning( disable : 4530 )
+#pragma warning( disable : 4786 )
+#endif
+
+#include <ctype.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <assert.h>
+
+// Help out windows:
+#if defined( _DEBUG ) && !defined( DEBUG )
+#define DEBUG
+#endif
+
+#ifdef TIXML_USE_STL
+	#include <string>
+ 	#include <iostream>
+	#include <sstream>
+	#define TIXML_STRING		std::string
+#else
+	#include "tinystr.h"
+	#define TIXML_STRING		TiXmlString
+#endif
+
+// Deprecated library function hell. Compilers want to use the
+// new safe versions. This probably doesn't fully address the problem,
+// but it gets closer. There are too many compilers for me to fully
+// test. If you get compilation troubles, undefine TIXML_SAFE
+#define TIXML_SAFE
+
+#ifdef TIXML_SAFE
+	#if defined(_MSC_VER) && (_MSC_VER >= 1400 )
+		// Microsoft visual studio, version 2005 and higher.
+		#define TIXML_SNPRINTF _snprintf_s
+		#define TIXML_SSCANF   sscanf_s
+	#elif defined(_MSC_VER) && (_MSC_VER >= 1200 )
+		// Microsoft visual studio, version 6 and higher.
+		//#pragma message( "Using _sn* functions." )
+		#define TIXML_SNPRINTF _snprintf
+		#define TIXML_SSCANF   sscanf
+	#elif defined(__GNUC__) && (__GNUC__ >= 3 )
+		// GCC version 3 and higher.s
+		//#warning( "Using sn* functions." )
+		#define TIXML_SNPRINTF snprintf
+		#define TIXML_SSCANF   sscanf
+	#else
+		#define TIXML_SNPRINTF snprintf
+		#define TIXML_SSCANF   sscanf
+	#endif
+#endif	
+
+class TiXmlDocument;
+class TiXmlElement;
+class TiXmlComment;
+class TiXmlUnknown;
+class TiXmlAttribute;
+class TiXmlText;
+class TiXmlDeclaration;
+class TiXmlParsingData;
+
+const int TIXML_MAJOR_VERSION = 2;
+const int TIXML_MINOR_VERSION = 6;
+const int TIXML_PATCH_VERSION = 2;
+
+/*	Internal structure for tracking location of items 
+	in the XML file.
+*/
+struct TiXmlCursor
+{
+	TiXmlCursor()		{ Clear(); }
+	void Clear()		{ row = col = -1; }
+
+	int row;	// 0 based.
+	int col;	// 0 based.
+};
+
+
+/**
+	Implements the interface to the "Visitor pattern" (see the Accept() method.)
+	If you call the Accept() method, it requires being passed a TiXmlVisitor
+	class to handle callbacks. For nodes that contain other nodes (Document, Element)
+	you will get called with a VisitEnter/VisitExit pair. Nodes that are always leaves
+	are simply called with Visit().
+
+	If you return 'true' from a Visit method, recursive parsing will continue. If you return
+	false, <b>no children of this node or its sibilings</b> will be Visited.
+
+	All flavors of Visit methods have a default implementation that returns 'true' (continue 
+	visiting). You need to only override methods that are interesting to you.
+
+	Generally Accept() is called on the TiXmlDocument, although all nodes suppert Visiting.
+
+	You should never change the document from a callback.
+
+	@sa TiXmlNode::Accept()
+*/
+class TiXmlVisitor
+{
+public:
+	virtual ~TiXmlVisitor() {}
+
+	/// Visit a document.
+	virtual bool VisitEnter( const TiXmlDocument& /*doc*/ )			{ return true; }
+	/// Visit a document.
+	virtual bool VisitExit( const TiXmlDocument& /*doc*/ )			{ return true; }
+
+	/// Visit an element.
+	virtual bool VisitEnter( const TiXmlElement& /*element*/, const TiXmlAttribute* /*firstAttribute*/ )	{ return true; }
+	/// Visit an element.
+	virtual bool VisitExit( const TiXmlElement& /*element*/ )		{ return true; }
+
+	/// Visit a declaration
+	virtual bool Visit( const TiXmlDeclaration& /*declaration*/ )	{ return true; }
+	/// Visit a text node
+	virtual bool Visit( const TiXmlText& /*text*/ )					{ return true; }
+	/// Visit a comment node
+	virtual bool Visit( const TiXmlComment& /*comment*/ )			{ return true; }
+	/// Visit an unknown node
+	virtual bool Visit( const TiXmlUnknown& /*unknown*/ )			{ return true; }
+};
+
+// Only used by Attribute::Query functions
+enum 
+{ 
+	TIXML_SUCCESS,
+	TIXML_NO_ATTRIBUTE,
+	TIXML_WRONG_TYPE
+};
+
+
+// Used by the parsing routines.
+enum TiXmlEncoding
+{
+	TIXML_ENCODING_UNKNOWN,
+	TIXML_ENCODING_UTF8,
+	TIXML_ENCODING_LEGACY
+};
+
+const TiXmlEncoding TIXML_DEFAULT_ENCODING = TIXML_ENCODING_UNKNOWN;
+
+/** TiXmlBase is a base class for every class in TinyXml.
+	It does little except to establish that TinyXml classes
+	can be printed and provide some utility functions.
+
+	In XML, the document and elements can contain
+	other elements and other types of nodes.
+
+	@verbatim
+	A Document can contain:	Element	(container or leaf)
+							Comment (leaf)
+							Unknown (leaf)
+							Declaration( leaf )
+
+	An Element can contain:	Element (container or leaf)
+							Text	(leaf)
+							Attributes (not on tree)
+							Comment (leaf)
+							Unknown (leaf)
+
+	A Decleration contains: Attributes (not on tree)
+	@endverbatim
+*/
+class TiXmlBase
+{
+	friend class TiXmlNode;
+	friend class TiXmlElement;
+	friend class TiXmlDocument;
+
+public:
+	TiXmlBase()	:	userData(0)		{}
+	virtual ~TiXmlBase()			{}
+
+	/**	All TinyXml classes can print themselves to a filestream
+		or the string class (TiXmlString in non-STL mode, std::string
+		in STL mode.) Either or both cfile and str can be null.
+		
+		This is a formatted print, and will insert 
+		tabs and newlines.
+		
+		(For an unformatted stream, use the << operator.)
+	*/
+	virtual void Print( FILE* cfile, int depth ) const = 0;
+
+	/**	The world does not agree on whether white space should be kept or
+		not. In order to make everyone happy, these global, static functions
+		are provided to set whether or not TinyXml will condense all white space
+		into a single space or not. The default is to condense. Note changing this
+		value is not thread safe.
+	*/
+	static void SetCondenseWhiteSpace( bool condense )		{ condenseWhiteSpace = condense; }
+
+	/// Return the current white space setting.
+	static bool IsWhiteSpaceCondensed()						{ return condenseWhiteSpace; }
+
+	/** Return the position, in the original source file, of this node or attribute.
+		The row and column are 1-based. (That is the first row and first column is
+		1,1). If the returns values are 0 or less, then the parser does not have
+		a row and column value.
+
+		Generally, the row and column value will be set when the TiXmlDocument::Load(),
+		TiXmlDocument::LoadFile(), or any TiXmlNode::Parse() is called. It will NOT be set
+		when the DOM was created from operator>>.
+
+		The values reflect the initial load. Once the DOM is modified programmatically
+		(by adding or changing nodes and attributes) the new values will NOT update to
+		reflect changes in the document.
+
+		There is a minor performance cost to computing the row and column. Computation
+		can be disabled if TiXmlDocument::SetTabSize() is called with 0 as the value.
+
+		@sa TiXmlDocument::SetTabSize()
+	*/
+	int Row() const			{ return location.row + 1; }
+	int Column() const		{ return location.col + 1; }	///< See Row()
+
+	void  SetUserData( void* user )			{ userData = user; }	///< Set a pointer to arbitrary user data.
+	void* GetUserData()						{ return userData; }	///< Get a pointer to arbitrary user data.
+	const void* GetUserData() const 		{ return userData; }	///< Get a pointer to arbitrary user data.
+
+	// Table that returs, for a given lead byte, the total number of bytes
+	// in the UTF-8 sequence.
+	static const int utf8ByteTable[256];
+
+	virtual const char* Parse(	const char* p, 
+								TiXmlParsingData* data, 
+								TiXmlEncoding encoding /*= TIXML_ENCODING_UNKNOWN */ ) = 0;
+
+	/** Expands entities in a string. Note this should not contian the tag's '<', '>', etc, 
+		or they will be transformed into entities!
+	*/
+	static void EncodeString( const TIXML_STRING& str, TIXML_STRING* out );
+
+	enum
+	{
+		TIXML_NO_ERROR = 0,
+		TIXML_ERROR,
+		TIXML_ERROR_OPENING_FILE,
+		TIXML_ERROR_PARSING_ELEMENT,
+		TIXML_ERROR_FAILED_TO_READ_ELEMENT_NAME,
+		TIXML_ERROR_READING_ELEMENT_VALUE,
+		TIXML_ERROR_READING_ATTRIBUTES,
+		TIXML_ERROR_PARSING_EMPTY,
+		TIXML_ERROR_READING_END_TAG,
+		TIXML_ERROR_PARSING_UNKNOWN,
+		TIXML_ERROR_PARSING_COMMENT,
+		TIXML_ERROR_PARSING_DECLARATION,
+		TIXML_ERROR_DOCUMENT_EMPTY,
+		TIXML_ERROR_EMBEDDED_NULL,
+		TIXML_ERROR_PARSING_CDATA,
+		TIXML_ERROR_DOCUMENT_TOP_ONLY,
+
+		TIXML_ERROR_STRING_COUNT
+	};
+
+protected:
+
+	static const char* SkipWhiteSpace( const char*, TiXmlEncoding encoding );
+
+	inline static bool IsWhiteSpace( char c )		
+	{ 
+		return ( isspace( (unsigned char) c ) || c == '\n' || c == '\r' ); 
+	}
+	inline static bool IsWhiteSpace( int c )
+	{
+		if ( c < 256 )
+			return IsWhiteSpace( (char) c );
+		return false;	// Again, only truly correct for English/Latin...but usually works.
+	}
+
+	#ifdef TIXML_USE_STL
+	static bool	StreamWhiteSpace( std::istream * in, TIXML_STRING * tag );
+	static bool StreamTo( std::istream * in, int character, TIXML_STRING * tag );
+	#endif
+
+	/*	Reads an XML name into the string provided. Returns
+		a pointer just past the last character of the name,
+		or 0 if the function has an error.
+	*/
+	static const char* ReadName( const char* p, TIXML_STRING* name, TiXmlEncoding encoding );
+
+	/*	Reads text. Returns a pointer past the given end tag.
+		Wickedly complex options, but it keeps the (sensitive) code in one place.
+	*/
+	static const char* ReadText(	const char* in,				// where to start
+									TIXML_STRING* text,			// the string read
+									bool ignoreWhiteSpace,		// whether to keep the white space
+									const char* endTag,			// what ends this text
+									bool ignoreCase,			// whether to ignore case in the end tag
+									TiXmlEncoding encoding );	// the current encoding
+
+	// If an entity has been found, transform it into a character.
+	static const char* GetEntity( const char* in, char* value, int* length, TiXmlEncoding encoding );
+
+	// Get a character, while interpreting entities.
+	// The length can be from 0 to 4 bytes.
+	inline static const char* GetChar( const char* p, char* _value, int* length, TiXmlEncoding encoding )
+	{
+		assert( p );
+		if ( encoding == TIXML_ENCODING_UTF8 )
+		{
+			*length = utf8ByteTable[ *((const unsigned char*)p) ];
+			assert( *length >= 0 && *length < 5 );
+		}
+		else
+		{
+			*length = 1;
+		}
+
+		if ( *length == 1 )
+		{
+			if ( *p == '&' )
+				return GetEntity( p, _value, length, encoding );
+			*_value = *p;
+			return p+1;
+		}
+		else if ( *length )
+		{
+			//strncpy( _value, p, *length );	// lots of compilers don't like this function (unsafe),
+												// and the null terminator isn't needed
+			for( int i=0; p[i] && i<*length; ++i ) {
+				_value[i] = p[i];
+			}
+			return p + (*length);
+		}
+		else
+		{
+			// Not valid text.
+			return 0;
+		}
+	}
+
+	// Return true if the next characters in the stream are any of the endTag sequences.
+	// Ignore case only works for english, and should only be relied on when comparing
+	// to English words: StringEqual( p, "version", true ) is fine.
+	static bool StringEqual(	const char* p,
+								const char* endTag,
+								bool ignoreCase,
+								TiXmlEncoding encoding );
+
+	static const char* errorString[ TIXML_ERROR_STRING_COUNT ];
+
+	TiXmlCursor location;
+
+    /// Field containing a generic user pointer
+	void*			userData;
+	
+	// None of these methods are reliable for any language except English.
+	// Good for approximation, not great for accuracy.
+	static int IsAlpha( unsigned char anyByte, TiXmlEncoding encoding );
+	static int IsAlphaNum( unsigned char anyByte, TiXmlEncoding encoding );
+	inline static int ToLower( int v, TiXmlEncoding encoding )
+	{
+		if ( encoding == TIXML_ENCODING_UTF8 )
+		{
+			if ( v < 128 ) return tolower( v );
+			return v;
+		}
+		else
+		{
+			return tolower( v );
+		}
+	}
+	static void ConvertUTF32ToUTF8( unsigned long input, char* output, int* length );
+
+private:
+	TiXmlBase( const TiXmlBase& );				// not implemented.
+	void operator=( const TiXmlBase& base );	// not allowed.
+
+	struct Entity
+	{
+		const char*     str;
+		unsigned int	strLength;
+		char		    chr;
+	};
+	enum
+	{
+		NUM_ENTITY = 5,
+		MAX_ENTITY_LENGTH = 6
+
+	};
+	static Entity entity[ NUM_ENTITY ];
+	static bool condenseWhiteSpace;
+};
+
+
+/** The parent class for everything in the Document Object Model.
+	(Except for attributes).
+	Nodes have siblings, a parent, and children. A node can be
+	in a document, or stand on its own. The type of a TiXmlNode
+	can be queried, and it can be cast to its more defined type.
+*/
+class TiXmlNode : public TiXmlBase
+{
+	friend class TiXmlDocument;
+	friend class TiXmlElement;
+
+public:
+	#ifdef TIXML_USE_STL	
+
+	    /** An input stream operator, for every class. Tolerant of newlines and
+		    formatting, but doesn't expect them.
+	    */
+	    friend std::istream& operator >> (std::istream& in, TiXmlNode& base);
+
+	    /** An output stream operator, for every class. Note that this outputs
+		    without any newlines or formatting, as opposed to Print(), which
+		    includes tabs and new lines.
+
+		    The operator<< and operator>> are not completely symmetric. Writing
+		    a node to a stream is very well defined. You'll get a nice stream
+		    of output, without any extra whitespace or newlines.
+		    
+		    But reading is not as well defined. (As it always is.) If you create
+		    a TiXmlElement (for example) and read that from an input stream,
+		    the text needs to define an element or junk will result. This is
+		    true of all input streams, but it's worth keeping in mind.
+
+		    A TiXmlDocument will read nodes until it reads a root element, and
+			all the children of that root element.
+	    */	
+	    friend std::ostream& operator<< (std::ostream& out, const TiXmlNode& base);
+
+		/// Appends the XML node or attribute to a std::string.
+		friend std::string& operator<< (std::string& out, const TiXmlNode& base );
+
+	#endif
+
+	/** The types of XML nodes supported by TinyXml. (All the
+			unsupported types are picked up by UNKNOWN.)
+	*/
+	enum NodeType
+	{
+		TINYXML_DOCUMENT,
+		TINYXML_ELEMENT,
+		TINYXML_COMMENT,
+		TINYXML_UNKNOWN,
+		TINYXML_TEXT,
+		TINYXML_DECLARATION,
+		TINYXML_TYPECOUNT
+	};
+
+	virtual ~TiXmlNode();
+
+	/** The meaning of 'value' changes for the specific type of
+		TiXmlNode.
+		@verbatim
+		Document:	filename of the xml file
+		Element:	name of the element
+		Comment:	the comment text
+		Unknown:	the tag contents
+		Text:		the text string
+		@endverbatim
+
+		The subclasses will wrap this function.
+	*/
+	const char *Value() const { return value.c_str (); }
+
+    #ifdef TIXML_USE_STL
+	/** Return Value() as a std::string. If you only use STL,
+	    this is more efficient than calling Value().
+		Only available in STL mode.
+	*/
+	const std::string& ValueStr() const { return value; }
+	#endif
+
+	const TIXML_STRING& ValueTStr() const { return value; }
+
+	/** Changes the value of the node. Defined as:
+		@verbatim
+		Document:	filename of the xml file
+		Element:	name of the element
+		Comment:	the comment text
+		Unknown:	the tag contents
+		Text:		the text string
+		@endverbatim
+	*/
+	void SetValue(const char * _value) { value = _value;}
+
+    #ifdef TIXML_USE_STL
+	/// STL std::string form.
+	void SetValue( const std::string& _value )	{ value = _value; }
+	#endif
+
+	/// Delete all the children of this node. Does not affect 'this'.
+	void Clear();
+
+	/// One step up the DOM.
+	TiXmlNode* Parent()							{ return parent; }
+	const TiXmlNode* Parent() const				{ return parent; }
+
+	const TiXmlNode* FirstChild()	const		{ return firstChild; }	///< The first child of this node. Will be null if there are no children.
+	TiXmlNode* FirstChild()						{ return firstChild; }
+	const TiXmlNode* FirstChild( const char * value ) const;			///< The first child of this node with the matching 'value'. Will be null if none found.
+	/// The first child of this node with the matching 'value'. Will be null if none found.
+	TiXmlNode* FirstChild( const char * _value ) {
+		// Call through to the const version - safe since nothing is changed. Exiting syntax: cast this to a const (always safe)
+		// call the method, cast the return back to non-const.
+		return const_cast< TiXmlNode* > ((const_cast< const TiXmlNode* >(this))->FirstChild( _value ));
+	}
+	const TiXmlNode* LastChild() const	{ return lastChild; }		/// The last child of this node. Will be null if there are no children.
+	TiXmlNode* LastChild()	{ return lastChild; }
+	
+	const TiXmlNode* LastChild( const char * value ) const;			/// The last child of this node matching 'value'. Will be null if there are no children.
+	TiXmlNode* LastChild( const char * _value ) {
+		return const_cast< TiXmlNode* > ((const_cast< const TiXmlNode* >(this))->LastChild( _value ));
+	}
+
+    #ifdef TIXML_USE_STL
+	const TiXmlNode* FirstChild( const std::string& _value ) const	{	return FirstChild (_value.c_str ());	}	///< STL std::string form.
+	TiXmlNode* FirstChild( const std::string& _value )				{	return FirstChild (_value.c_str ());	}	///< STL std::string form.
+	const TiXmlNode* LastChild( const std::string& _value ) const	{	return LastChild (_value.c_str ());	}	///< STL std::string form.
+	TiXmlNode* LastChild( const std::string& _value )				{	return LastChild (_value.c_str ());	}	///< STL std::string form.
+	#endif
+
+	/** An alternate way to walk the children of a node.
+		One way to iterate over nodes is:
+		@verbatim
+			for( child = parent->FirstChild(); child; child = child->NextSibling() )
+		@endverbatim
+
+		IterateChildren does the same thing with the syntax:
+		@verbatim
+			child = 0;
+			while( child = parent->IterateChildren( child ) )
+		@endverbatim
+
+		IterateChildren takes the previous child as input and finds
+		the next one. If the previous child is null, it returns the
+		first. IterateChildren will return null when done.
+	*/
+	const TiXmlNode* IterateChildren( const TiXmlNode* previous ) const;
+	TiXmlNode* IterateChildren( const TiXmlNode* previous ) {
+		return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->IterateChildren( previous ) );
+	}
+
+	/// This flavor of IterateChildren searches for children with a particular 'value'
+	const TiXmlNode* IterateChildren( const char * value, const TiXmlNode* previous ) const;
+	TiXmlNode* IterateChildren( const char * _value, const TiXmlNode* previous ) {
+		return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->IterateChildren( _value, previous ) );
+	}
+
+    #ifdef TIXML_USE_STL
+	const TiXmlNode* IterateChildren( const std::string& _value, const TiXmlNode* previous ) const	{	return IterateChildren (_value.c_str (), previous);	}	///< STL std::string form.
+	TiXmlNode* IterateChildren( const std::string& _value, const TiXmlNode* previous ) {	return IterateChildren (_value.c_str (), previous);	}	///< STL std::string form.
+	#endif
+
+	/** Add a new node related to this. Adds a child past the LastChild.
+		Returns a pointer to the new object or NULL if an error occured.
+	*/
+	TiXmlNode* InsertEndChild( const TiXmlNode& addThis );
+
+
+	/** Add a new node related to this. Adds a child past the LastChild.
+
+		NOTE: the node to be added is passed by pointer, and will be
+		henceforth owned (and deleted) by tinyXml. This method is efficient
+		and avoids an extra copy, but should be used with care as it
+		uses a different memory model than the other insert functions.
+
+		@sa InsertEndChild
+	*/
+	TiXmlNode* LinkEndChild( TiXmlNode* addThis );
+
+	/** Add a new node related to this. Adds a child before the specified child.
+		Returns a pointer to the new object or NULL if an error occured.
+	*/
+	TiXmlNode* InsertBeforeChild( TiXmlNode* beforeThis, const TiXmlNode& addThis );
+
+	/** Add a new node related to this. Adds a child after the specified child.
+		Returns a pointer to the new object or NULL if an error occured.
+	*/
+	TiXmlNode* InsertAfterChild(  TiXmlNode* afterThis, const TiXmlNode& addThis );
+
+	/** Replace a child of this node.
+		Returns a pointer to the new object or NULL if an error occured.
+	*/
+	TiXmlNode* ReplaceChild( TiXmlNode* replaceThis, const TiXmlNode& withThis );
+
+	/// Delete a child of this node.
+	bool RemoveChild( TiXmlNode* removeThis );
+
+	/// Navigate to a sibling node.
+	const TiXmlNode* PreviousSibling() const			{ return prev; }
+	TiXmlNode* PreviousSibling()						{ return prev; }
+
+	/// Navigate to a sibling node.
+	const TiXmlNode* PreviousSibling( const char * ) const;
+	TiXmlNode* PreviousSibling( const char *_prev ) {
+		return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->PreviousSibling( _prev ) );
+	}
+
+    #ifdef TIXML_USE_STL
+	const TiXmlNode* PreviousSibling( const std::string& _value ) const	{	return PreviousSibling (_value.c_str ());	}	///< STL std::string form.
+	TiXmlNode* PreviousSibling( const std::string& _value ) 			{	return PreviousSibling (_value.c_str ());	}	///< STL std::string form.
+	const TiXmlNode* NextSibling( const std::string& _value) const		{	return NextSibling (_value.c_str ());	}	///< STL std::string form.
+	TiXmlNode* NextSibling( const std::string& _value) 					{	return NextSibling (_value.c_str ());	}	///< STL std::string form.
+	#endif
+
+	/// Navigate to a sibling node.
+	const TiXmlNode* NextSibling() const				{ return next; }
+	TiXmlNode* NextSibling()							{ return next; }
+
+	/// Navigate to a sibling node with the given 'value'.
+	const TiXmlNode* NextSibling( const char * ) const;
+	TiXmlNode* NextSibling( const char* _next ) {
+		return const_cast< TiXmlNode* >( (const_cast< const TiXmlNode* >(this))->NextSibling( _next ) );
+	}
+
+	/** Convenience function to get through elements.
+		Calls NextSibling and ToElement. Will skip all non-Element
+		nodes. Returns 0 if there is not another element.
+	*/
+	const TiXmlElement* NextSiblingElement() const;
+	TiXmlElement* NextSiblingElement() {
+		return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->NextSiblingElement() );
+	}
+
+	/** Convenience function to get through elements.
+		Calls NextSibling and ToElement. Will skip all non-Element
+		nodes. Returns 0 if there is not another element.
+	*/
+	const TiXmlElement* NextSiblingElement( const char * ) const;
+	TiXmlElement* NextSiblingElement( const char *_next ) {
+		return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->NextSiblingElement( _next ) );
+	}
+
+    #ifdef TIXML_USE_STL
+	const TiXmlElement* NextSiblingElement( const std::string& _value) const	{	return NextSiblingElement (_value.c_str ());	}	///< STL std::string form.
+	TiXmlElement* NextSiblingElement( const std::string& _value)				{	return NextSiblingElement (_value.c_str ());	}	///< STL std::string form.
+	#endif
+
+	/// Convenience function to get through elements.
+	const TiXmlElement* FirstChildElement()	const;
+	TiXmlElement* FirstChildElement() {
+		return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->FirstChildElement() );
+	}
+
+	/// Convenience function to get through elements.
+	const TiXmlElement* FirstChildElement( const char * _value ) const;
+	TiXmlElement* FirstChildElement( const char * _value ) {
+		return const_cast< TiXmlElement* >( (const_cast< const TiXmlNode* >(this))->FirstChildElement( _value ) );
+	}
+
+    #ifdef TIXML_USE_STL
+	const TiXmlElement* FirstChildElement( const std::string& _value ) const	{	return FirstChildElement (_value.c_str ());	}	///< STL std::string form.
+	TiXmlElement* FirstChildElement( const std::string& _value )				{	return FirstChildElement (_value.c_str ());	}	///< STL std::string form.
+	#endif
+
+	/** Query the type (as an enumerated value, above) of this node.
+		The possible types are: TINYXML_DOCUMENT, TINYXML_ELEMENT, TINYXML_COMMENT,
+								TINYXML_UNKNOWN, TINYXML_TEXT, and TINYXML_DECLARATION.
+	*/
+	int Type() const	{ return type; }
+
+	/** Return a pointer to the Document this node lives in.
+		Returns null if not in a document.
+	*/
+	const TiXmlDocument* GetDocument() const;
+	TiXmlDocument* GetDocument() {
+		return const_cast< TiXmlDocument* >( (const_cast< const TiXmlNode* >(this))->GetDocument() );
+	}
+
+	/// Returns true if this node has no children.
+	bool NoChildren() const						{ return !firstChild; }
+
+	virtual const TiXmlDocument*    ToDocument()    const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual const TiXmlElement*     ToElement()     const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual const TiXmlComment*     ToComment()     const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual const TiXmlUnknown*     ToUnknown()     const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual const TiXmlText*        ToText()        const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual const TiXmlDeclaration* ToDeclaration() const { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+
+	virtual TiXmlDocument*          ToDocument()    { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual TiXmlElement*           ToElement()	    { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual TiXmlComment*           ToComment()     { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual TiXmlUnknown*           ToUnknown()	    { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual TiXmlText*	            ToText()        { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+	virtual TiXmlDeclaration*       ToDeclaration() { return 0; } ///< Cast to a more defined type. Will return null if not of the requested type.
+
+	/** Create an exact duplicate of this node and return it. The memory must be deleted
+		by the caller. 
+	*/
+	virtual TiXmlNode* Clone() const = 0;
+
+	/** Accept a hierchical visit the nodes in the TinyXML DOM. Every node in the 
+		XML tree will be conditionally visited and the host will be called back
+		via the TiXmlVisitor interface.
+
+		This is essentially a SAX interface for TinyXML. (Note however it doesn't re-parse
+		the XML for the callbacks, so the performance of TinyXML is unchanged by using this
+		interface versus any other.)
+
+		The interface has been based on ideas from:
+
+		- http://www.saxproject.org/
+		- http://c2.com/cgi/wiki?HierarchicalVisitorPattern 
+
+		Which are both good references for "visiting".
+
+		An example of using Accept():
+		@verbatim
+		TiXmlPrinter printer;
+		tinyxmlDoc.Accept( &printer );
+		const char* xmlcstr = printer.CStr();
+		@endverbatim
+	*/
+	virtual bool Accept( TiXmlVisitor* visitor ) const = 0;
+
+protected:
+	TiXmlNode( NodeType _type );
+
+	// Copy to the allocated object. Shared functionality between Clone, Copy constructor,
+	// and the assignment operator.
+	void CopyTo( TiXmlNode* target ) const;
+
+	#ifdef TIXML_USE_STL
+	    // The real work of the input operator.
+	virtual void StreamIn( std::istream* in, TIXML_STRING* tag ) = 0;
+	#endif
+
+	// Figure out what is at *p, and parse it. Returns null if it is not an xml node.
+	TiXmlNode* Identify( const char* start, TiXmlEncoding encoding );
+
+	TiXmlNode*		parent;
+	NodeType		type;
+
+	TiXmlNode*		firstChild;
+	TiXmlNode*		lastChild;
+
+	TIXML_STRING	value;
+
+	TiXmlNode*		prev;
+	TiXmlNode*		next;
+
+private:
+	TiXmlNode( const TiXmlNode& );				// not implemented.
+	void operator=( const TiXmlNode& base );	// not allowed.
+};
+
+
+/** An attribute is a name-value pair. Elements have an arbitrary
+	number of attributes, each with a unique name.
+
+	@note The attributes are not TiXmlNodes, since they are not
+		  part of the tinyXML document object model. There are other
+		  suggested ways to look at this problem.
+*/
+class TiXmlAttribute : public TiXmlBase
+{
+	friend class TiXmlAttributeSet;
+
+public:
+	/// Construct an empty attribute.
+	TiXmlAttribute() : TiXmlBase()
+	{
+		document = 0;
+		prev = next = 0;
+	}
+
+	#ifdef TIXML_USE_STL
+	/// std::string constructor.
+	TiXmlAttribute( const std::string& _name, const std::string& _value )
+	{
+		name = _name;
+		value = _value;
+		document = 0;
+		prev = next = 0;
+	}
+	#endif
+
+	/// Construct an attribute with a name and value.
+	TiXmlAttribute( const char * _name, const char * _value )
+	{
+		name = _name;
+		value = _value;
+		document = 0;
+		prev = next = 0;
+	}
+
+	const char*		Name()  const		{ return name.c_str(); }		///< Return the name of this attribute.
+	const char*		Value() const		{ return value.c_str(); }		///< Return the value of this attribute.
+	#ifdef TIXML_USE_STL
+	const std::string& ValueStr() const	{ return value; }				///< Return the value of this attribute.
+	#endif
+	int				IntValue() const;									///< Return the value of this attribute, converted to an integer.
+	double			DoubleValue() const;								///< Return the value of this attribute, converted to a double.
+
+	// Get the tinyxml string representation
+	const TIXML_STRING& NameTStr() const { return name; }
+
+	/** QueryIntValue examines the value string. It is an alternative to the
+		IntValue() method with richer error checking.
+		If the value is an integer, it is stored in 'value' and 
+		the call returns TIXML_SUCCESS. If it is not
+		an integer, it returns TIXML_WRONG_TYPE.
+
+		A specialized but useful call. Note that for success it returns 0,
+		which is the opposite of almost all other TinyXml calls.
+	*/
+	int QueryIntValue( int* _value ) const;
+	/// QueryDoubleValue examines the value string. See QueryIntValue().
+	int QueryDoubleValue( double* _value ) const;
+
+	void SetName( const char* _name )	{ name = _name; }				///< Set the name of this attribute.
+	void SetValue( const char* _value )	{ value = _value; }				///< Set the value.
+
+	void SetIntValue( int _value );										///< Set the value from an integer.
+	void SetDoubleValue( double _value );								///< Set the value from a double.
+
+    #ifdef TIXML_USE_STL
+	/// STL std::string form.
+	void SetName( const std::string& _name )	{ name = _name; }	
+	/// STL std::string form.	
+	void SetValue( const std::string& _value )	{ value = _value; }
+	#endif
+
+	/// Get the next sibling attribute in the DOM. Returns null at end.
+	const TiXmlAttribute* Next() const;
+	TiXmlAttribute* Next() {
+		return const_cast< TiXmlAttribute* >( (const_cast< const TiXmlAttribute* >(this))->Next() ); 
+	}
+
+	/// Get the previous sibling attribute in the DOM. Returns null at beginning.
+	const TiXmlAttribute* Previous() const;
+	TiXmlAttribute* Previous() {
+		return const_cast< TiXmlAttribute* >( (const_cast< const TiXmlAttribute* >(this))->Previous() ); 
+	}
+
+	bool operator==( const TiXmlAttribute& rhs ) const { return rhs.name == name; }
+	bool operator<( const TiXmlAttribute& rhs )	 const { return name < rhs.name; }
+	bool operator>( const TiXmlAttribute& rhs )  const { return name > rhs.name; }
+
+	/*	Attribute parsing starts: first letter of the name
+						 returns: the next char after the value end quote
+	*/
+	virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding );
+
+	// Prints this Attribute to a FILE stream.
+	virtual void Print( FILE* cfile, int depth ) const {
+		Print( cfile, depth, 0 );
+	}
+	void Print( FILE* cfile, int depth, TIXML_STRING* str ) const;
+
+	// [internal use]
+	// Set the document pointer so the attribute can report errors.
+	void SetDocument( TiXmlDocument* doc )	{ document = doc; }
+
+private:
+	TiXmlAttribute( const TiXmlAttribute& );				// not implemented.
+	void operator=( const TiXmlAttribute& base );	// not allowed.
+
+	TiXmlDocument*	document;	// A pointer back to a document, for error reporting.
+	TIXML_STRING name;
+	TIXML_STRING value;
+	TiXmlAttribute*	prev;
+	TiXmlAttribute*	next;
+};
+
+
+/*	A class used to manage a group of attributes.
+	It is only used internally, both by the ELEMENT and the DECLARATION.
+	
+	The set can be changed transparent to the Element and Declaration
+	classes that use it, but NOT transparent to the Attribute
+	which has to implement a next() and previous() method. Which makes
+	it a bit problematic and prevents the use of STL.
+
+	This version is implemented with circular lists because:
+		- I like circular lists
+		- it demonstrates some independence from the (typical) doubly linked list.
+*/
+class TiXmlAttributeSet
+{
+public:
+	TiXmlAttributeSet();
+	~TiXmlAttributeSet();
+
+	void Add( TiXmlAttribute* attribute );
+	void Remove( TiXmlAttribute* attribute );
+
+	const TiXmlAttribute* First()	const	{ return ( sentinel.next == &sentinel ) ? 0 : sentinel.next; }
+	TiXmlAttribute* First()					{ return ( sentinel.next == &sentinel ) ? 0 : sentinel.next; }
+	const TiXmlAttribute* Last() const		{ return ( sentinel.prev == &sentinel ) ? 0 : sentinel.prev; }
+	TiXmlAttribute* Last()					{ return ( sentinel.prev == &sentinel ) ? 0 : sentinel.prev; }
+
+	TiXmlAttribute*	Find( const char* _name ) const;
+	TiXmlAttribute* FindOrCreate( const char* _name );
+
+#	ifdef TIXML_USE_STL
+	TiXmlAttribute*	Find( const std::string& _name ) const;
+	TiXmlAttribute* FindOrCreate( const std::string& _name );
+#	endif
+
+
+private:
+	//*ME:	Because of hidden/disabled copy-construktor in TiXmlAttribute (sentinel-element),
+	//*ME:	this class must be also use a hidden/disabled copy-constructor !!!
+	TiXmlAttributeSet( const TiXmlAttributeSet& );	// not allowed
+	void operator=( const TiXmlAttributeSet& );	// not allowed (as TiXmlAttribute)
+
+	TiXmlAttribute sentinel;
+};
+
+
+/** The element is a container class. It has a value, the element name,
+	and can contain other elements, text, comments, and unknowns.
+	Elements also contain an arbitrary number of attributes.
+*/
+class TiXmlElement : public TiXmlNode
+{
+public:
+	/// Construct an element.
+	TiXmlElement (const char * in_value);
+
+	#ifdef TIXML_USE_STL
+	/// std::string constructor.
+	TiXmlElement( const std::string& _value );
+	#endif
+
+	TiXmlElement( const TiXmlElement& );
+
+	TiXmlElement& operator=( const TiXmlElement& base );
+
+	virtual ~TiXmlElement();
+
+	/** Given an attribute name, Attribute() returns the value
+		for the attribute of that name, or null if none exists.
+	*/
+	const char* Attribute( const char* name ) const;
+
+	/** Given an attribute name, Attribute() returns the value
+		for the attribute of that name, or null if none exists.
+		If the attribute exists and can be converted to an integer,
+		the integer value will be put in the return 'i', if 'i'
+		is non-null.
+	*/
+	const char* Attribute( const char* name, int* i ) const;
+
+	/** Given an attribute name, Attribute() returns the value
+		for the attribute of that name, or null if none exists.
+		If the attribute exists and can be converted to an double,
+		the double value will be put in the return 'd', if 'd'
+		is non-null.
+	*/
+	const char* Attribute( const char* name, double* d ) const;
+
+	/** QueryIntAttribute examines the attribute - it is an alternative to the
+		Attribute() method with richer error checking.
+		If the attribute is an integer, it is stored in 'value' and 
+		the call returns TIXML_SUCCESS. If it is not
+		an integer, it returns TIXML_WRONG_TYPE. If the attribute
+		does not exist, then TIXML_NO_ATTRIBUTE is returned.
+	*/	
+	int QueryIntAttribute( const char* name, int* _value ) const;
+	/// QueryUnsignedAttribute examines the attribute - see QueryIntAttribute().
+	int QueryUnsignedAttribute( const char* name, unsigned* _value ) const;
+	/** QueryBoolAttribute examines the attribute - see QueryIntAttribute(). 
+		Note that '1', 'true', or 'yes' are considered true, while '0', 'false'
+		and 'no' are considered false.
+	*/
+	int QueryBoolAttribute( const char* name, bool* _value ) const;
+	/// QueryDoubleAttribute examines the attribute - see QueryIntAttribute().
+	int QueryDoubleAttribute( const char* name, double* _value ) const;
+	/// QueryFloatAttribute examines the attribute - see QueryIntAttribute().
+	int QueryFloatAttribute( const char* name, float* _value ) const {
+		double d;
+		int result = QueryDoubleAttribute( name, &d );
+		if ( result == TIXML_SUCCESS ) {
+			*_value = (float)d;
+		}
+		return result;
+	}
+
+    #ifdef TIXML_USE_STL
+	/// QueryStringAttribute examines the attribute - see QueryIntAttribute().
+	int QueryStringAttribute( const char* name, std::string* _value ) const {
+		const char* cstr = Attribute( name );
+		if ( cstr ) {
+			*_value = std::string( cstr );
+			return TIXML_SUCCESS;
+		}
+		return TIXML_NO_ATTRIBUTE;
+	}
+
+	/** Template form of the attribute query which will try to read the
+		attribute into the specified type. Very easy, very powerful, but
+		be careful to make sure to call this with the correct type.
+		
+		NOTE: This method doesn't work correctly for 'string' types that contain spaces.
+
+		@return TIXML_SUCCESS, TIXML_WRONG_TYPE, or TIXML_NO_ATTRIBUTE
+	*/
+	template< typename T > int QueryValueAttribute( const std::string& name, T* outValue ) const
+	{
+		const TiXmlAttribute* node = attributeSet.Find( name );
+		if ( !node )
+			return TIXML_NO_ATTRIBUTE;
+
+		std::stringstream sstream( node->ValueStr() );
+		sstream >> *outValue;
+		if ( !sstream.fail() )
+			return TIXML_SUCCESS;
+		return TIXML_WRONG_TYPE;
+	}
+
+	int QueryValueAttribute( const std::string& name, std::string* outValue ) const
+	{
+		const TiXmlAttribute* node = attributeSet.Find( name );
+		if ( !node )
+			return TIXML_NO_ATTRIBUTE;
+		*outValue = node->ValueStr();
+		return TIXML_SUCCESS;
+	}
+	#endif
+
+	/** Sets an attribute of name to a given value. The attribute
+		will be created if it does not exist, or changed if it does.
+	*/
+	void SetAttribute( const char* name, const char * _value );
+
+    #ifdef TIXML_USE_STL
+	const std::string* Attribute( const std::string& name ) const;
+	const std::string* Attribute( const std::string& name, int* i ) const;
+	const std::string* Attribute( const std::string& name, double* d ) const;
+	int QueryIntAttribute( const std::string& name, int* _value ) const;
+	int QueryDoubleAttribute( const std::string& name, double* _value ) const;
+
+	/// STL std::string form.
+	void SetAttribute( const std::string& name, const std::string& _value );
+	///< STL std::string form.
+	void SetAttribute( const std::string& name, int _value );
+	///< STL std::string form.
+	void SetDoubleAttribute( const std::string& name, double value );
+	#endif
+
+	/** Sets an attribute of name to a given value. The attribute
+		will be created if it does not exist, or changed if it does.
+	*/
+	void SetAttribute( const char * name, int value );
+
+	/** Sets an attribute of name to a given value. The attribute
+		will be created if it does not exist, or changed if it does.
+	*/
+	void SetDoubleAttribute( const char * name, double value );
+
+	/** Deletes an attribute with the given name.
+	*/
+	void RemoveAttribute( const char * name );
+    #ifdef TIXML_USE_STL
+	void RemoveAttribute( const std::string& name )	{	RemoveAttribute (name.c_str ());	}	///< STL std::string form.
+	#endif
+
+	const TiXmlAttribute* FirstAttribute() const	{ return attributeSet.First(); }		///< Access the first attribute in this element.
+	TiXmlAttribute* FirstAttribute() 				{ return attributeSet.First(); }
+	const TiXmlAttribute* LastAttribute()	const 	{ return attributeSet.Last(); }		///< Access the last attribute in this element.
+	TiXmlAttribute* LastAttribute()					{ return attributeSet.Last(); }
+
+	/** Convenience function for easy access to the text inside an element. Although easy
+		and concise, GetText() is limited compared to getting the TiXmlText child
+		and accessing it directly.
+	
+		If the first child of 'this' is a TiXmlText, the GetText()
+		returns the character string of the Text node, else null is returned.
+
+		This is a convenient method for getting the text of simple contained text:
+		@verbatim
+		<foo>This is text</foo>
+		const char* str = fooElement->GetText();
+		@endverbatim
+
+		'str' will be a pointer to "This is text". 
+		
+		Note that this function can be misleading. If the element foo was created from
+		this XML:
+		@verbatim
+		<foo><b>This is text</b></foo> 
+		@endverbatim
+
+		then the value of str would be null. The first child node isn't a text node, it is
+		another element. From this XML:
+		@verbatim
+		<foo>This is <b>text</b></foo> 
+		@endverbatim
+		GetText() will return "This is ".
+
+		WARNING: GetText() accesses a child node - don't become confused with the 
+				 similarly named TiXmlHandle::Text() and TiXmlNode::ToText() which are 
+				 safe type casts on the referenced node.
+	*/
+	const char* GetText() const;
+
+	/// Creates a new Element and returns it - the returned element is a copy.
+	virtual TiXmlNode* Clone() const;
+	// Print the Element to a FILE stream.
+	virtual void Print( FILE* cfile, int depth ) const;
+
+	/*	Attribtue parsing starts: next char past '<'
+						 returns: next char past '>'
+	*/
+	virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding );
+
+	virtual const TiXmlElement*     ToElement()     const { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+	virtual TiXmlElement*           ToElement()	          { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+
+	/** Walk the XML tree visiting this node and all of its children. 
+	*/
+	virtual bool Accept( TiXmlVisitor* visitor ) const;
+
+protected:
+
+	void CopyTo( TiXmlElement* target ) const;
+	void ClearThis();	// like clear, but initializes 'this' object as well
+
+	// Used to be public [internal use]
+	#ifdef TIXML_USE_STL
+	virtual void StreamIn( std::istream * in, TIXML_STRING * tag );
+	#endif
+	/*	[internal use]
+		Reads the "value" of the element -- another element, or text.
+		This should terminate with the current end tag.
+	*/
+	const char* ReadValue( const char* in, TiXmlParsingData* prevData, TiXmlEncoding encoding );
+
+private:
+	TiXmlAttributeSet attributeSet;
+};
+
+
+/**	An XML comment.
+*/
+class TiXmlComment : public TiXmlNode
+{
+public:
+	/// Constructs an empty comment.
+	TiXmlComment() : TiXmlNode( TiXmlNode::TINYXML_COMMENT ) {}
+	/// Construct a comment from text.
+	TiXmlComment( const char* _value ) : TiXmlNode( TiXmlNode::TINYXML_COMMENT ) {
+		SetValue( _value );
+	}
+	TiXmlComment( const TiXmlComment& );
+	TiXmlComment& operator=( const TiXmlComment& base );
+
+	virtual ~TiXmlComment()	{}
+
+	/// Returns a copy of this Comment.
+	virtual TiXmlNode* Clone() const;
+	// Write this Comment to a FILE stream.
+	virtual void Print( FILE* cfile, int depth ) const;
+
+	/*	Attribtue parsing starts: at the ! of the !--
+						 returns: next char past '>'
+	*/
+	virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding );
+
+	virtual const TiXmlComment*  ToComment() const	{ return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+	virtual		  TiXmlComment*  ToComment()		{ return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+
+	/** Walk the XML tree visiting this node and all of its children. 
+	*/
+	virtual bool Accept( TiXmlVisitor* visitor ) const;
+
+protected:
+	void CopyTo( TiXmlComment* target ) const;
+
+	// used to be public
+	#ifdef TIXML_USE_STL
+	virtual void StreamIn( std::istream * in, TIXML_STRING * tag );
+	#endif
+//	virtual void StreamOut( TIXML_OSTREAM * out ) const;
+
+private:
+
+};
+
+
+/** XML text. A text node can have 2 ways to output the next. "normal" output 
+	and CDATA. It will default to the mode it was parsed from the XML file and
+	you generally want to leave it alone, but you can change the output mode with 
+	SetCDATA() and query it with CDATA().
+*/
+class TiXmlText : public TiXmlNode
+{
+	friend class TiXmlElement;
+public:
+	/** Constructor for text element. By default, it is treated as 
+		normal, encoded text. If you want it be output as a CDATA text
+		element, set the parameter _cdata to 'true'
+	*/
+	TiXmlText (const char * initValue ) : TiXmlNode (TiXmlNode::TINYXML_TEXT)
+	{
+		SetValue( initValue );
+		cdata = false;
+	}
+	virtual ~TiXmlText() {}
+
+	#ifdef TIXML_USE_STL
+	/// Constructor.
+	TiXmlText( const std::string& initValue ) : TiXmlNode (TiXmlNode::TINYXML_TEXT)
+	{
+		SetValue( initValue );
+		cdata = false;
+	}
+	#endif
+
+	TiXmlText( const TiXmlText& copy ) : TiXmlNode( TiXmlNode::TINYXML_TEXT )	{ copy.CopyTo( this ); }
+	TiXmlText& operator=( const TiXmlText& base )							 	{ base.CopyTo( this ); return *this; }
+
+	// Write this text object to a FILE stream.
+	virtual void Print( FILE* cfile, int depth ) const;
+
+	/// Queries whether this represents text using a CDATA section.
+	bool CDATA() const				{ return cdata; }
+	/// Turns on or off a CDATA representation of text.
+	void SetCDATA( bool _cdata )	{ cdata = _cdata; }
+
+	virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding );
+
+	virtual const TiXmlText* ToText() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+	virtual TiXmlText*       ToText()       { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+
+	/** Walk the XML tree visiting this node and all of its children. 
+	*/
+	virtual bool Accept( TiXmlVisitor* content ) const;
+
+protected :
+	///  [internal use] Creates a new Element and returns it.
+	virtual TiXmlNode* Clone() const;
+	void CopyTo( TiXmlText* target ) const;
+
+	bool Blank() const;	// returns true if all white space and new lines
+	// [internal use]
+	#ifdef TIXML_USE_STL
+	virtual void StreamIn( std::istream * in, TIXML_STRING * tag );
+	#endif
+
+private:
+	bool cdata;			// true if this should be input and output as a CDATA style text element
+};
+
+
+/** In correct XML the declaration is the first entry in the file.
+	@verbatim
+		<?xml version="1.0" standalone="yes"?>
+	@endverbatim
+
+	TinyXml will happily read or write files without a declaration,
+	however. There are 3 possible attributes to the declaration:
+	version, encoding, and standalone.
+
+	Note: In this version of the code, the attributes are
+	handled as special cases, not generic attributes, simply
+	because there can only be at most 3 and they are always the same.
+*/
+class TiXmlDeclaration : public TiXmlNode
+{
+public:
+	/// Construct an empty declaration.
+	TiXmlDeclaration()   : TiXmlNode( TiXmlNode::TINYXML_DECLARATION ) {}
+
+#ifdef TIXML_USE_STL
+	/// Constructor.
+	TiXmlDeclaration(	const std::string& _version,
+						const std::string& _encoding,
+						const std::string& _standalone );
+#endif
+
+	/// Construct.
+	TiXmlDeclaration(	const char* _version,
+						const char* _encoding,
+						const char* _standalone );
+
+	TiXmlDeclaration( const TiXmlDeclaration& copy );
+	TiXmlDeclaration& operator=( const TiXmlDeclaration& copy );
+
+	virtual ~TiXmlDeclaration()	{}
+
+	/// Version. Will return an empty string if none was found.
+	const char *Version() const			{ return version.c_str (); }
+	/// Encoding. Will return an empty string if none was found.
+	const char *Encoding() const		{ return encoding.c_str (); }
+	/// Is this a standalone document?
+	const char *Standalone() const		{ return standalone.c_str (); }
+
+	/// Creates a copy of this Declaration and returns it.
+	virtual TiXmlNode* Clone() const;
+	// Print this declaration to a FILE stream.
+	virtual void Print( FILE* cfile, int depth, TIXML_STRING* str ) const;
+	virtual void Print( FILE* cfile, int depth ) const {
+		Print( cfile, depth, 0 );
+	}
+
+	virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding );
+
+	virtual const TiXmlDeclaration* ToDeclaration() const { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+	virtual TiXmlDeclaration*       ToDeclaration()       { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+
+	/** Walk the XML tree visiting this node and all of its children. 
+	*/
+	virtual bool Accept( TiXmlVisitor* visitor ) const;
+
+protected:
+	void CopyTo( TiXmlDeclaration* target ) const;
+	// used to be public
+	#ifdef TIXML_USE_STL
+	virtual void StreamIn( std::istream * in, TIXML_STRING * tag );
+	#endif
+
+private:
+
+	TIXML_STRING version;
+	TIXML_STRING encoding;
+	TIXML_STRING standalone;
+};
+
+
+/** Any tag that tinyXml doesn't recognize is saved as an
+	unknown. It is a tag of text, but should not be modified.
+	It will be written back to the XML, unchanged, when the file
+	is saved.
+
+	DTD tags get thrown into TiXmlUnknowns.
+*/
+class TiXmlUnknown : public TiXmlNode
+{
+public:
+	TiXmlUnknown() : TiXmlNode( TiXmlNode::TINYXML_UNKNOWN )	{}
+	virtual ~TiXmlUnknown() {}
+
+	TiXmlUnknown( const TiXmlUnknown& copy ) : TiXmlNode( TiXmlNode::TINYXML_UNKNOWN )		{ copy.CopyTo( this ); }
+	TiXmlUnknown& operator=( const TiXmlUnknown& copy )										{ copy.CopyTo( this ); return *this; }
+
+	/// Creates a copy of this Unknown and returns it.
+	virtual TiXmlNode* Clone() const;
+	// Print this Unknown to a FILE stream.
+	virtual void Print( FILE* cfile, int depth ) const;
+
+	virtual const char* Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding );
+
+	virtual const TiXmlUnknown*     ToUnknown()     const	{ return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+	virtual TiXmlUnknown*           ToUnknown()				{ return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+
+	/** Walk the XML tree visiting this node and all of its children. 
+	*/
+	virtual bool Accept( TiXmlVisitor* content ) const;
+
+protected:
+	void CopyTo( TiXmlUnknown* target ) const;
+
+	#ifdef TIXML_USE_STL
+	virtual void StreamIn( std::istream * in, TIXML_STRING * tag );
+	#endif
+
+private:
+
+};
+
+
+/** Always the top level node. A document binds together all the
+	XML pieces. It can be saved, loaded, and printed to the screen.
+	The 'value' of a document node is the xml file name.
+*/
+class TiXmlDocument : public TiXmlNode
+{
+public:
+	/// Create an empty document, that has no name.
+	TiXmlDocument();
+	/// Create a document with a name. The name of the document is also the filename of the xml.
+	TiXmlDocument( const char * documentName );
+
+	#ifdef TIXML_USE_STL
+	/// Constructor.
+	TiXmlDocument( const std::string& documentName );
+	#endif
+
+	TiXmlDocument( const TiXmlDocument& copy );
+	TiXmlDocument& operator=( const TiXmlDocument& copy );
+
+	virtual ~TiXmlDocument() {}
+
+	/** Load a file using the current document value.
+		Returns true if successful. Will delete any existing
+		document data before loading.
+	*/
+	bool LoadFile( TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING );
+	/// Save a file using the current document value. Returns true if successful.
+	bool SaveFile() const;
+	/// Load a file using the given filename. Returns true if successful.
+	bool LoadFile( const char * filename, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING );
+	/// Save a file using the given filename. Returns true if successful.
+	bool SaveFile( const char * filename ) const;
+	/** Load a file using the given FILE*. Returns true if successful. Note that this method
+		doesn't stream - the entire object pointed at by the FILE*
+		will be interpreted as an XML file. TinyXML doesn't stream in XML from the current
+		file location. Streaming may be added in the future.
+	*/
+	bool LoadFile( FILE*, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING );
+	/// Save a file using the given FILE*. Returns true if successful.
+	bool SaveFile( FILE* ) const;
+
+	#ifdef TIXML_USE_STL
+	bool LoadFile( const std::string& filename, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING )			///< STL std::string version.
+	{
+		return LoadFile( filename.c_str(), encoding );
+	}
+	bool SaveFile( const std::string& filename ) const		///< STL std::string version.
+	{
+		return SaveFile( filename.c_str() );
+	}
+	#endif
+
+	/** Parse the given null terminated block of xml data. Passing in an encoding to this
+		method (either TIXML_ENCODING_LEGACY or TIXML_ENCODING_UTF8 will force TinyXml
+		to use that encoding, regardless of what TinyXml might otherwise try to detect.
+	*/
+	virtual const char* Parse( const char* p, TiXmlParsingData* data = 0, TiXmlEncoding encoding = TIXML_DEFAULT_ENCODING );
+
+	/** Get the root element -- the only top level element -- of the document.
+		In well formed XML, there should only be one. TinyXml is tolerant of
+		multiple elements at the document level.
+	*/
+	const TiXmlElement* RootElement() const		{ return FirstChildElement(); }
+	TiXmlElement* RootElement()					{ return FirstChildElement(); }
+
+	/** If an error occurs, Error will be set to true. Also,
+		- The ErrorId() will contain the integer identifier of the error (not generally useful)
+		- The ErrorDesc() method will return the name of the error. (very useful)
+		- The ErrorRow() and ErrorCol() will return the location of the error (if known)
+	*/	
+	bool Error() const						{ return error; }
+
+	/// Contains a textual (english) description of the error if one occurs.
+	const char * ErrorDesc() const	{ return errorDesc.c_str (); }
+
+	/** Generally, you probably want the error string ( ErrorDesc() ). But if you
+		prefer the ErrorId, this function will fetch it.
+	*/
+	int ErrorId()	const				{ return errorId; }
+
+	/** Returns the location (if known) of the error. The first column is column 1, 
+		and the first row is row 1. A value of 0 means the row and column wasn't applicable
+		(memory errors, for example, have no row/column) or the parser lost the error. (An
+		error in the error reporting, in that case.)
+
+		@sa SetTabSize, Row, Column
+	*/
+	int ErrorRow() const	{ return errorLocation.row+1; }
+	int ErrorCol() const	{ return errorLocation.col+1; }	///< The column where the error occured. See ErrorRow()
+
+	/** SetTabSize() allows the error reporting functions (ErrorRow() and ErrorCol())
+		to report the correct values for row and column. It does not change the output
+		or input in any way.
+		
+		By calling this method, with a tab size
+		greater than 0, the row and column of each node and attribute is stored
+		when the file is loaded. Very useful for tracking the DOM back in to
+		the source file.
+
+		The tab size is required for calculating the location of nodes. If not
+		set, the default of 4 is used. The tabsize is set per document. Setting
+		the tabsize to 0 disables row/column tracking.
+
+		Note that row and column tracking is not supported when using operator>>.
+
+		The tab size needs to be enabled before the parse or load. Correct usage:
+		@verbatim
+		TiXmlDocument doc;
+		doc.SetTabSize( 8 );
+		doc.Load( "myfile.xml" );
+		@endverbatim
+
+		@sa Row, Column
+	*/
+	void SetTabSize( int _tabsize )		{ tabsize = _tabsize; }
+
+	int TabSize() const	{ return tabsize; }
+
+	/** If you have handled the error, it can be reset with this call. The error
+		state is automatically cleared if you Parse a new XML block.
+	*/
+	void ClearError()						{	error = false; 
+												errorId = 0; 
+												errorDesc = ""; 
+												errorLocation.row = errorLocation.col = 0; 
+												//errorLocation.last = 0; 
+											}
+
+	/** Write the document to standard out using formatted printing ("pretty print"). */
+	void Print() const						{ Print( stdout, 0 ); }
+
+	/* Write the document to a string using formatted printing ("pretty print"). This
+		will allocate a character array (new char[]) and return it as a pointer. The
+		calling code pust call delete[] on the return char* to avoid a memory leak.
+	*/
+	//char* PrintToMemory() const; 
+
+	/// Print this Document to a FILE stream.
+	virtual void Print( FILE* cfile, int depth = 0 ) const;
+	// [internal use]
+	void SetError( int err, const char* errorLocation, TiXmlParsingData* prevData, TiXmlEncoding encoding );
+
+	virtual const TiXmlDocument*    ToDocument()    const { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+	virtual TiXmlDocument*          ToDocument()          { return this; } ///< Cast to a more defined type. Will return null not of the requested type.
+
+	/** Walk the XML tree visiting this node and all of its children. 
+	*/
+	virtual bool Accept( TiXmlVisitor* content ) const;
+
+protected :
+	// [internal use]
+	virtual TiXmlNode* Clone() const;
+	#ifdef TIXML_USE_STL
+	virtual void StreamIn( std::istream * in, TIXML_STRING * tag );
+	#endif
+
+private:
+	void CopyTo( TiXmlDocument* target ) const;
+
+	bool error;
+	int  errorId;
+	TIXML_STRING errorDesc;
+	int tabsize;
+	TiXmlCursor errorLocation;
+	bool useMicrosoftBOM;		// the UTF-8 BOM were found when read. Note this, and try to write.
+};
+
+
+/**
+	A TiXmlHandle is a class that wraps a node pointer with null checks; this is
+	an incredibly useful thing. Note that TiXmlHandle is not part of the TinyXml
+	DOM structure. It is a separate utility class.
+
+	Take an example:
+	@verbatim
+	<Document>
+		<Element attributeA = "valueA">
+			<Child attributeB = "value1" />
+			<Child attributeB = "value2" />
+		</Element>
+	<Document>
+	@endverbatim
+
+	Assuming you want the value of "attributeB" in the 2nd "Child" element, it's very 
+	easy to write a *lot* of code that looks like:
+
+	@verbatim
+	TiXmlElement* root = document.FirstChildElement( "Document" );
+	if ( root )
+	{
+		TiXmlElement* element = root->FirstChildElement( "Element" );
+		if ( element )
+		{
+			TiXmlElement* child = element->FirstChildElement( "Child" );
+			if ( child )
+			{
+				TiXmlElement* child2 = child->NextSiblingElement( "Child" );
+				if ( child2 )
+				{
+					// Finally do something useful.
+	@endverbatim
+
+	And that doesn't even cover "else" cases. TiXmlHandle addresses the verbosity
+	of such code. A TiXmlHandle checks for null	pointers so it is perfectly safe 
+	and correct to use:
+
+	@verbatim
+	TiXmlHandle docHandle( &document );
+	TiXmlElement* child2 = docHandle.FirstChild( "Document" ).FirstChild( "Element" ).Child( "Child", 1 ).ToElement();
+	if ( child2 )
+	{
+		// do something useful
+	@endverbatim
+
+	Which is MUCH more concise and useful.
+
+	It is also safe to copy handles - internally they are nothing more than node pointers.
+	@verbatim
+	TiXmlHandle handleCopy = handle;
+	@endverbatim
+
+	What they should not be used for is iteration:
+
+	@verbatim
+	int i=0; 
+	while ( true )
+	{
+		TiXmlElement* child = docHandle.FirstChild( "Document" ).FirstChild( "Element" ).Child( "Child", i ).ToElement();
+		if ( !child )
+			break;
+		// do something
+		++i;
+	}
+	@endverbatim
+
+	It seems reasonable, but it is in fact two embedded while loops. The Child method is 
+	a linear walk to find the element, so this code would iterate much more than it needs 
+	to. Instead, prefer:
+
+	@verbatim
+	TiXmlElement* child = docHandle.FirstChild( "Document" ).FirstChild( "Element" ).FirstChild( "Child" ).ToElement();
+
+	for( child; child; child=child->NextSiblingElement() )
+	{
+		// do something
+	}
+	@endverbatim
+*/
+class TiXmlHandle
+{
+public:
+	/// Create a handle from any node (at any depth of the tree.) This can be a null pointer.
+	TiXmlHandle( TiXmlNode* _node )					{ this->node = _node; }
+	/// Copy constructor
+	TiXmlHandle( const TiXmlHandle& ref )			{ this->node = ref.node; }
+	TiXmlHandle operator=( const TiXmlHandle& ref ) { if ( &ref != this ) this->node = ref.node; return *this; }
+
+	/// Return a handle to the first child node.
+	TiXmlHandle FirstChild() const;
+	/// Return a handle to the first child node with the given name.
+	TiXmlHandle FirstChild( const char * value ) const;
+	/// Return a handle to the first child element.
+	TiXmlHandle FirstChildElement() const;
+	/// Return a handle to the first child element with the given name.
+	TiXmlHandle FirstChildElement( const char * value ) const;
+
+	/** Return a handle to the "index" child with the given name. 
+		The first child is 0, the second 1, etc.
+	*/
+	TiXmlHandle Child( const char* value, int index ) const;
+	/** Return a handle to the "index" child. 
+		The first child is 0, the second 1, etc.
+	*/
+	TiXmlHandle Child( int index ) const;
+	/** Return a handle to the "index" child element with the given name. 
+		The first child element is 0, the second 1, etc. Note that only TiXmlElements
+		are indexed: other types are not counted.
+	*/
+	TiXmlHandle ChildElement( const char* value, int index ) const;
+	/** Return a handle to the "index" child element. 
+		The first child element is 0, the second 1, etc. Note that only TiXmlElements
+		are indexed: other types are not counted.
+	*/
+	TiXmlHandle ChildElement( int index ) const;
+
+	#ifdef TIXML_USE_STL
+	TiXmlHandle FirstChild( const std::string& _value ) const				{ return FirstChild( _value.c_str() ); }
+	TiXmlHandle FirstChildElement( const std::string& _value ) const		{ return FirstChildElement( _value.c_str() ); }
+
+	TiXmlHandle Child( const std::string& _value, int index ) const			{ return Child( _value.c_str(), index ); }
+	TiXmlHandle ChildElement( const std::string& _value, int index ) const	{ return ChildElement( _value.c_str(), index ); }
+	#endif
+
+	/** Return the handle as a TiXmlNode. This may return null.
+	*/
+	TiXmlNode* ToNode() const			{ return node; } 
+	/** Return the handle as a TiXmlElement. This may return null.
+	*/
+	TiXmlElement* ToElement() const		{ return ( ( node && node->ToElement() ) ? node->ToElement() : 0 ); }
+	/**	Return the handle as a TiXmlText. This may return null.
+	*/
+	TiXmlText* ToText() const			{ return ( ( node && node->ToText() ) ? node->ToText() : 0 ); }
+	/** Return the handle as a TiXmlUnknown. This may return null.
+	*/
+	TiXmlUnknown* ToUnknown() const		{ return ( ( node && node->ToUnknown() ) ? node->ToUnknown() : 0 ); }
+
+	/** @deprecated use ToNode. 
+		Return the handle as a TiXmlNode. This may return null.
+	*/
+	TiXmlNode* Node() const			{ return ToNode(); } 
+	/** @deprecated use ToElement. 
+		Return the handle as a TiXmlElement. This may return null.
+	*/
+	TiXmlElement* Element() const	{ return ToElement(); }
+	/**	@deprecated use ToText()
+		Return the handle as a TiXmlText. This may return null.
+	*/
+	TiXmlText* Text() const			{ return ToText(); }
+	/** @deprecated use ToUnknown()
+		Return the handle as a TiXmlUnknown. This may return null.
+	*/
+	TiXmlUnknown* Unknown() const	{ return ToUnknown(); }
+
+private:
+	TiXmlNode* node;
+};
+
+
+/** Print to memory functionality. The TiXmlPrinter is useful when you need to:
+
+	-# Print to memory (especially in non-STL mode)
+	-# Control formatting (line endings, etc.)
+
+	When constructed, the TiXmlPrinter is in its default "pretty printing" mode.
+	Before calling Accept() you can call methods to control the printing
+	of the XML document. After TiXmlNode::Accept() is called, the printed document can
+	be accessed via the CStr(), Str(), and Size() methods.
+
+	TiXmlPrinter uses the Visitor API.
+	@verbatim
+	TiXmlPrinter printer;
+	printer.SetIndent( "\t" );
+
+	doc.Accept( &printer );
+	fprintf( stdout, "%s", printer.CStr() );
+	@endverbatim
+*/
+class TiXmlPrinter : public TiXmlVisitor
+{
+public:
+	TiXmlPrinter() : depth( 0 ), simpleTextPrint( false ),
+					 buffer(), indent( "    " ), lineBreak( "\n" ) {}
+
+	virtual bool VisitEnter( const TiXmlDocument& doc );
+	virtual bool VisitExit( const TiXmlDocument& doc );
+
+	virtual bool VisitEnter( const TiXmlElement& element, const TiXmlAttribute* firstAttribute );
+	virtual bool VisitExit( const TiXmlElement& element );
+
+	virtual bool Visit( const TiXmlDeclaration& declaration );
+	virtual bool Visit( const TiXmlText& text );
+	virtual bool Visit( const TiXmlComment& comment );
+	virtual bool Visit( const TiXmlUnknown& unknown );
+
+	/** Set the indent characters for printing. By default 4 spaces
+		but tab (\t) is also useful, or null/empty string for no indentation.
+	*/
+	void SetIndent( const char* _indent )			{ indent = _indent ? _indent : "" ; }
+	/// Query the indention string.
+	const char* Indent()							{ return indent.c_str(); }
+	/** Set the line breaking string. By default set to newline (\n). 
+		Some operating systems prefer other characters, or can be
+		set to the null/empty string for no indenation.
+	*/
+	void SetLineBreak( const char* _lineBreak )		{ lineBreak = _lineBreak ? _lineBreak : ""; }
+	/// Query the current line breaking string.
+	const char* LineBreak()							{ return lineBreak.c_str(); }
+
+	/** Switch over to "stream printing" which is the most dense formatting without 
+		linebreaks. Common when the XML is needed for network transmission.
+	*/
+	void SetStreamPrinting()						{ indent = "";
+													  lineBreak = "";
+													}	
+	/// Return the result.
+	const char* CStr()								{ return buffer.c_str(); }
+	/// Return the length of the result string.
+	size_t Size()									{ return buffer.size(); }
+
+	#ifdef TIXML_USE_STL
+	/// Return the result.
+	const std::string& Str()						{ return buffer; }
+	#endif
+
+private:
+	void DoIndent()	{
+		for( int i=0; i<depth; ++i )
+			buffer += indent;
+	}
+	void DoLineBreak() {
+		buffer += lineBreak;
+	}
+
+	int depth;
+	bool simpleTextPrint;
+	TIXML_STRING buffer;
+	TIXML_STRING indent;
+	TIXML_STRING lineBreak;
+};
+
+
+#ifdef _MSC_VER
+#pragma warning( pop )
+#endif
+
+#endif
diff --git a/sfntly/cpp/src/test/tinyxml/tinyxmlerror.cpp b/sfntly/cpp/src/test/tinyxml/tinyxmlerror.cpp
new file mode 100644
index 0000000..538c21d
--- /dev/null
+++ b/sfntly/cpp/src/test/tinyxml/tinyxmlerror.cpp
@@ -0,0 +1,52 @@
+/*
+www.sourceforge.net/projects/tinyxml
+Original code (2.0 and earlier )copyright (c) 2000-2006 Lee Thomason (www.grinninglizard.com)
+
+This software is provided 'as-is', without any express or implied 
+warranty. In no event will the authors be held liable for any 
+damages arising from the use of this software.
+
+Permission is granted to anyone to use this software for any 
+purpose, including commercial applications, and to alter it and 
+redistribute it freely, subject to the following restrictions:
+
+1. The origin of this software must not be misrepresented; you must
+not claim that you wrote the original software. If you use this
+software in a product, an acknowledgment in the product documentation
+would be appreciated but is not required.
+
+2. Altered source versions must be plainly marked as such, and
+must not be misrepresented as being the original software.
+
+3. This notice may not be removed or altered from any source
+distribution.
+*/
+
+#include "tinyxml.h"
+
+// The goal of the seperate error file is to make the first
+// step towards localization. tinyxml (currently) only supports
+// english error messages, but the could now be translated.
+//
+// It also cleans up the code a bit.
+//
+
+const char* TiXmlBase::errorString[ TiXmlBase::TIXML_ERROR_STRING_COUNT ] =
+{
+	"No error",
+	"Error",
+	"Failed to open file",
+	"Error parsing Element.",
+	"Failed to read Element name",
+	"Error reading Element value.",
+	"Error reading Attributes.",
+	"Error: empty tag.",
+	"Error reading end tag.",
+	"Error parsing Unknown.",
+	"Error parsing Comment.",
+	"Error parsing Declaration.",
+	"Error document empty.",
+	"Error null (0) or unexpected EOF found in input stream.",
+	"Error parsing CDATA.",
+	"Error when TiXmlDocument added to document, because TiXmlDocument can only be at the root.",
+};
diff --git a/sfntly/cpp/src/test/tinyxml/tinyxmlparser.cpp b/sfntly/cpp/src/test/tinyxml/tinyxmlparser.cpp
new file mode 100644
index 0000000..81b7eae
--- /dev/null
+++ b/sfntly/cpp/src/test/tinyxml/tinyxmlparser.cpp
@@ -0,0 +1,1638 @@
+/*
+www.sourceforge.net/projects/tinyxml
+Original code by Lee Thomason (www.grinninglizard.com)
+
+This software is provided 'as-is', without any express or implied 
+warranty. In no event will the authors be held liable for any 
+damages arising from the use of this software.
+
+Permission is granted to anyone to use this software for any 
+purpose, including commercial applications, and to alter it and 
+redistribute it freely, subject to the following restrictions:
+
+1. The origin of this software must not be misrepresented; you must 
+not claim that you wrote the original software. If you use this
+software in a product, an acknowledgment in the product documentation
+would be appreciated but is not required.
+
+2. Altered source versions must be plainly marked as such, and 
+must not be misrepresented as being the original software.
+
+3. This notice may not be removed or altered from any source 
+distribution.
+*/
+
+#include <ctype.h>
+#include <stddef.h>
+
+#include "tinyxml.h"
+
+//#define DEBUG_PARSER
+#if defined( DEBUG_PARSER )
+#	if defined( DEBUG ) && defined( _MSC_VER )
+#		include <windows.h>
+#		define TIXML_LOG OutputDebugString
+#	else
+#		define TIXML_LOG printf
+#	endif
+#endif
+
+// Note tha "PutString" hardcodes the same list. This
+// is less flexible than it appears. Changing the entries
+// or order will break putstring.	
+TiXmlBase::Entity TiXmlBase::entity[ TiXmlBase::NUM_ENTITY ] = 
+{
+	{ "&amp;",  5, '&' },
+	{ "&lt;",   4, '<' },
+	{ "&gt;",   4, '>' },
+	{ "&quot;", 6, '\"' },
+	{ "&apos;", 6, '\'' }
+};
+
+// Bunch of unicode info at:
+//		http://www.unicode.org/faq/utf_bom.html
+// Including the basic of this table, which determines the #bytes in the
+// sequence from the lead byte. 1 placed for invalid sequences --
+// although the result will be junk, pass it through as much as possible.
+// Beware of the non-characters in UTF-8:	
+//				ef bb bf (Microsoft "lead bytes")
+//				ef bf be
+//				ef bf bf 
+
+const unsigned char TIXML_UTF_LEAD_0 = 0xefU;
+const unsigned char TIXML_UTF_LEAD_1 = 0xbbU;
+const unsigned char TIXML_UTF_LEAD_2 = 0xbfU;
+
+const int TiXmlBase::utf8ByteTable[256] = 
+{
+	//	0	1	2	3	4	5	6	7	8	9	a	b	c	d	e	f
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x00
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x10
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x20
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x30
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x40
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x50
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x60
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x70	End of ASCII range
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x80 0x80 to 0xc1 invalid
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0x90 
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0xa0 
+		1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	// 0xb0 
+		1,	1,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	// 0xc0 0xc2 to 0xdf 2 byte
+		2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	2,	// 0xd0
+		3,	3,	3,	3,	3,	3,	3,	3,	3,	3,	3,	3,	3,	3,	3,	3,	// 0xe0 0xe0 to 0xef 3 byte
+		4,	4,	4,	4,	4,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1,	1	// 0xf0 0xf0 to 0xf4 4 byte, 0xf5 and higher invalid
+};
+
+
+void TiXmlBase::ConvertUTF32ToUTF8( unsigned long input, char* output, int* length )
+{
+	const unsigned long BYTE_MASK = 0xBF;
+	const unsigned long BYTE_MARK = 0x80;
+	const unsigned long FIRST_BYTE_MARK[7] = { 0x00, 0x00, 0xC0, 0xE0, 0xF0, 0xF8, 0xFC };
+
+	if (input < 0x80) 
+		*length = 1;
+	else if ( input < 0x800 )
+		*length = 2;
+	else if ( input < 0x10000 )
+		*length = 3;
+	else if ( input < 0x200000 )
+		*length = 4;
+	else
+		{ *length = 0; return; }	// This code won't covert this correctly anyway.
+
+	output += *length;
+
+	// Scary scary fall throughs.
+	switch (*length) 
+	{
+		case 4:
+			--output; 
+			*output = (char)((input | BYTE_MARK) & BYTE_MASK); 
+			input >>= 6;
+		case 3:
+			--output; 
+			*output = (char)((input | BYTE_MARK) & BYTE_MASK); 
+			input >>= 6;
+		case 2:
+			--output; 
+			*output = (char)((input | BYTE_MARK) & BYTE_MASK); 
+			input >>= 6;
+		case 1:
+			--output; 
+			*output = (char)(input | FIRST_BYTE_MARK[*length]);
+	}
+}
+
+
+/*static*/ int TiXmlBase::IsAlpha( unsigned char anyByte, TiXmlEncoding /*encoding*/ )
+{
+	// This will only work for low-ascii, everything else is assumed to be a valid
+	// letter. I'm not sure this is the best approach, but it is quite tricky trying
+	// to figure out alhabetical vs. not across encoding. So take a very 
+	// conservative approach.
+
+//	if ( encoding == TIXML_ENCODING_UTF8 )
+//	{
+		if ( anyByte < 127 )
+			return isalpha( anyByte );
+		else
+			return 1;	// What else to do? The unicode set is huge...get the english ones right.
+//	}
+//	else
+//	{
+//		return isalpha( anyByte );
+//	}
+}
+
+
+/*static*/ int TiXmlBase::IsAlphaNum( unsigned char anyByte, TiXmlEncoding /*encoding*/ )
+{
+	// This will only work for low-ascii, everything else is assumed to be a valid
+	// letter. I'm not sure this is the best approach, but it is quite tricky trying
+	// to figure out alhabetical vs. not across encoding. So take a very 
+	// conservative approach.
+
+//	if ( encoding == TIXML_ENCODING_UTF8 )
+//	{
+		if ( anyByte < 127 )
+			return isalnum( anyByte );
+		else
+			return 1;	// What else to do? The unicode set is huge...get the english ones right.
+//	}
+//	else
+//	{
+//		return isalnum( anyByte );
+//	}
+}
+
+
+class TiXmlParsingData
+{
+	friend class TiXmlDocument;
+  public:
+	void Stamp( const char* now, TiXmlEncoding encoding );
+
+	const TiXmlCursor& Cursor() const	{ return cursor; }
+
+  private:
+	// Only used by the document!
+	TiXmlParsingData( const char* start, int _tabsize, int row, int col )
+	{
+		assert( start );
+		stamp = start;
+		tabsize = _tabsize;
+		cursor.row = row;
+		cursor.col = col;
+	}
+
+	TiXmlCursor		cursor;
+	const char*		stamp;
+	int				tabsize;
+};
+
+
+void TiXmlParsingData::Stamp( const char* now, TiXmlEncoding encoding )
+{
+	assert( now );
+
+	// Do nothing if the tabsize is 0.
+	if ( tabsize < 1 )
+	{
+		return;
+	}
+
+	// Get the current row, column.
+	int row = cursor.row;
+	int col = cursor.col;
+	const char* p = stamp;
+	assert( p );
+
+	while ( p < now )
+	{
+		// Treat p as unsigned, so we have a happy compiler.
+		const unsigned char* pU = (const unsigned char*)p;
+
+		// Code contributed by Fletcher Dunn: (modified by lee)
+		switch (*pU) {
+			case 0:
+				// We *should* never get here, but in case we do, don't
+				// advance past the terminating null character, ever
+				return;
+
+			case '\r':
+				// bump down to the next line
+				++row;
+				col = 0;				
+				// Eat the character
+				++p;
+
+				// Check for \r\n sequence, and treat this as a single character
+				if (*p == '\n') {
+					++p;
+				}
+				break;
+
+			case '\n':
+				// bump down to the next line
+				++row;
+				col = 0;
+
+				// Eat the character
+				++p;
+
+				// Check for \n\r sequence, and treat this as a single
+				// character.  (Yes, this bizarre thing does occur still
+				// on some arcane platforms...)
+				if (*p == '\r') {
+					++p;
+				}
+				break;
+
+			case '\t':
+				// Eat the character
+				++p;
+
+				// Skip to next tab stop
+				col = (col / tabsize + 1) * tabsize;
+				break;
+
+			case TIXML_UTF_LEAD_0:
+				if ( encoding == TIXML_ENCODING_UTF8 )
+				{
+					if ( *(p+1) && *(p+2) )
+					{
+						// In these cases, don't advance the column. These are
+						// 0-width spaces.
+						if ( *(pU+1)==TIXML_UTF_LEAD_1 && *(pU+2)==TIXML_UTF_LEAD_2 )
+							p += 3;	
+						else if ( *(pU+1)==0xbfU && *(pU+2)==0xbeU )
+							p += 3;	
+						else if ( *(pU+1)==0xbfU && *(pU+2)==0xbfU )
+							p += 3;	
+						else
+							{ p +=3; ++col; }	// A normal character.
+					}
+				}
+				else
+				{
+					++p;
+					++col;
+				}
+				break;
+
+			default:
+				if ( encoding == TIXML_ENCODING_UTF8 )
+				{
+					// Eat the 1 to 4 byte utf8 character.
+					int step = TiXmlBase::utf8ByteTable[*((const unsigned char*)p)];
+					if ( step == 0 )
+						step = 1;		// Error case from bad encoding, but handle gracefully.
+					p += step;
+
+					// Just advance one column, of course.
+					++col;
+				}
+				else
+				{
+					++p;
+					++col;
+				}
+				break;
+		}
+	}
+	cursor.row = row;
+	cursor.col = col;
+	assert( cursor.row >= -1 );
+	assert( cursor.col >= -1 );
+	stamp = p;
+	assert( stamp );
+}
+
+
+const char* TiXmlBase::SkipWhiteSpace( const char* p, TiXmlEncoding encoding )
+{
+	if ( !p || !*p )
+	{
+		return 0;
+	}
+	if ( encoding == TIXML_ENCODING_UTF8 )
+	{
+		while ( *p )
+		{
+			const unsigned char* pU = (const unsigned char*)p;
+			
+			// Skip the stupid Microsoft UTF-8 Byte order marks
+			if (	*(pU+0)==TIXML_UTF_LEAD_0
+				 && *(pU+1)==TIXML_UTF_LEAD_1 
+				 && *(pU+2)==TIXML_UTF_LEAD_2 )
+			{
+				p += 3;
+				continue;
+			}
+			else if(*(pU+0)==TIXML_UTF_LEAD_0
+				 && *(pU+1)==0xbfU
+				 && *(pU+2)==0xbeU )
+			{
+				p += 3;
+				continue;
+			}
+			else if(*(pU+0)==TIXML_UTF_LEAD_0
+				 && *(pU+1)==0xbfU
+				 && *(pU+2)==0xbfU )
+			{
+				p += 3;
+				continue;
+			}
+
+			if ( IsWhiteSpace( *p ) )		// Still using old rules for white space.
+				++p;
+			else
+				break;
+		}
+	}
+	else
+	{
+		while ( *p && IsWhiteSpace( *p ) )
+			++p;
+	}
+
+	return p;
+}
+
+#ifdef TIXML_USE_STL
+/*static*/ bool TiXmlBase::StreamWhiteSpace( std::istream * in, TIXML_STRING * tag )
+{
+	for( ;; )
+	{
+		if ( !in->good() ) return false;
+
+		int c = in->peek();
+		// At this scope, we can't get to a document. So fail silently.
+		if ( !IsWhiteSpace( c ) || c <= 0 )
+			return true;
+
+		*tag += (char) in->get();
+	}
+}
+
+/*static*/ bool TiXmlBase::StreamTo( std::istream * in, int character, TIXML_STRING * tag )
+{
+	//assert( character > 0 && character < 128 );	// else it won't work in utf-8
+	while ( in->good() )
+	{
+		int c = in->peek();
+		if ( c == character )
+			return true;
+		if ( c <= 0 )		// Silent failure: can't get document at this scope
+			return false;
+
+		in->get();
+		*tag += (char) c;
+	}
+	return false;
+}
+#endif
+
+// One of TinyXML's more performance demanding functions. Try to keep the memory overhead down. The
+// "assign" optimization removes over 10% of the execution time.
+//
+const char* TiXmlBase::ReadName( const char* p, TIXML_STRING * name, TiXmlEncoding encoding )
+{
+	// Oddly, not supported on some comilers,
+	//name->clear();
+	// So use this:
+	*name = "";
+	assert( p );
+
+	// Names start with letters or underscores.
+	// Of course, in unicode, tinyxml has no idea what a letter *is*. The
+	// algorithm is generous.
+	//
+	// After that, they can be letters, underscores, numbers,
+	// hyphens, or colons. (Colons are valid ony for namespaces,
+	// but tinyxml can't tell namespaces from names.)
+	if (    p && *p 
+		 && ( IsAlpha( (unsigned char) *p, encoding ) || *p == '_' ) )
+	{
+		const char* start = p;
+		while(		p && *p
+				&&	(		IsAlphaNum( (unsigned char ) *p, encoding ) 
+						 || *p == '_'
+						 || *p == '-'
+						 || *p == '.'
+						 || *p == ':' ) )
+		{
+			//(*name) += *p; // expensive
+			++p;
+		}
+		if ( p-start > 0 ) {
+			name->assign( start, p-start );
+		}
+		return p;
+	}
+	return 0;
+}
+
+const char* TiXmlBase::GetEntity( const char* p, char* value, int* length, TiXmlEncoding encoding )
+{
+	// Presume an entity, and pull it out.
+    TIXML_STRING ent;
+	int i;
+	*length = 0;
+
+	if ( *(p+1) && *(p+1) == '#' && *(p+2) )
+	{
+		unsigned long ucs = 0;
+		ptrdiff_t delta = 0;
+		unsigned mult = 1;
+
+		if ( *(p+2) == 'x' )
+		{
+			// Hexadecimal.
+			if ( !*(p+3) ) return 0;
+
+			const char* q = p+3;
+			q = strchr( q, ';' );
+
+			if ( !q || !*q ) return 0;
+
+			delta = q-p;
+			--q;
+
+			while ( *q != 'x' )
+			{
+				if ( *q >= '0' && *q <= '9' )
+					ucs += mult * (*q - '0');
+				else if ( *q >= 'a' && *q <= 'f' )
+					ucs += mult * (*q - 'a' + 10);
+				else if ( *q >= 'A' && *q <= 'F' )
+					ucs += mult * (*q - 'A' + 10 );
+				else 
+					return 0;
+				mult *= 16;
+				--q;
+			}
+		}
+		else
+		{
+			// Decimal.
+			if ( !*(p+2) ) return 0;
+
+			const char* q = p+2;
+			q = strchr( q, ';' );
+
+			if ( !q || !*q ) return 0;
+
+			delta = q-p;
+			--q;
+
+			while ( *q != '#' )
+			{
+				if ( *q >= '0' && *q <= '9' )
+					ucs += mult * (*q - '0');
+				else 
+					return 0;
+				mult *= 10;
+				--q;
+			}
+		}
+		if ( encoding == TIXML_ENCODING_UTF8 )
+		{
+			// convert the UCS to UTF-8
+			ConvertUTF32ToUTF8( ucs, value, length );
+		}
+		else
+		{
+			*value = (char)ucs;
+			*length = 1;
+		}
+		return p + delta + 1;
+	}
+
+	// Now try to match it.
+	for( i=0; i<NUM_ENTITY; ++i )
+	{
+		if ( strncmp( entity[i].str, p, entity[i].strLength ) == 0 )
+		{
+			assert( strlen( entity[i].str ) == entity[i].strLength );
+			*value = entity[i].chr;
+			*length = 1;
+			return ( p + entity[i].strLength );
+		}
+	}
+
+	// So it wasn't an entity, its unrecognized, or something like that.
+	*value = *p;	// Don't put back the last one, since we return it!
+	//*length = 1;	// Leave unrecognized entities - this doesn't really work.
+					// Just writes strange XML.
+	return p+1;
+}
+
+
+bool TiXmlBase::StringEqual( const char* p,
+							 const char* tag,
+							 bool ignoreCase,
+							 TiXmlEncoding encoding )
+{
+	assert( p );
+	assert( tag );
+	if ( !p || !*p )
+	{
+		assert( 0 );
+		return false;
+	}
+
+	const char* q = p;
+
+	if ( ignoreCase )
+	{
+		while ( *q && *tag && ToLower( *q, encoding ) == ToLower( *tag, encoding ) )
+		{
+			++q;
+			++tag;
+		}
+
+		if ( *tag == 0 )
+			return true;
+	}
+	else
+	{
+		while ( *q && *tag && *q == *tag )
+		{
+			++q;
+			++tag;
+		}
+
+		if ( *tag == 0 )		// Have we found the end of the tag, and everything equal?
+			return true;
+	}
+	return false;
+}
+
+const char* TiXmlBase::ReadText(	const char* p, 
+									TIXML_STRING * text, 
+									bool trimWhiteSpace, 
+									const char* endTag, 
+									bool caseInsensitive,
+									TiXmlEncoding encoding )
+{
+    *text = "";
+	if (    !trimWhiteSpace			// certain tags always keep whitespace
+		 || !condenseWhiteSpace )	// if true, whitespace is always kept
+	{
+		// Keep all the white space.
+		while (	   p && *p
+				&& !StringEqual( p, endTag, caseInsensitive, encoding )
+			  )
+		{
+			int len;
+			char cArr[4] = { 0, 0, 0, 0 };
+			p = GetChar( p, cArr, &len, encoding );
+			text->append( cArr, len );
+		}
+	}
+	else
+	{
+		bool whitespace = false;
+
+		// Remove leading white space:
+		p = SkipWhiteSpace( p, encoding );
+		while (	   p && *p
+				&& !StringEqual( p, endTag, caseInsensitive, encoding ) )
+		{
+			if ( *p == '\r' || *p == '\n' )
+			{
+				whitespace = true;
+				++p;
+			}
+			else if ( IsWhiteSpace( *p ) )
+			{
+				whitespace = true;
+				++p;
+			}
+			else
+			{
+				// If we've found whitespace, add it before the
+				// new character. Any whitespace just becomes a space.
+				if ( whitespace )
+				{
+					(*text) += ' ';
+					whitespace = false;
+				}
+				int len;
+				char cArr[4] = { 0, 0, 0, 0 };
+				p = GetChar( p, cArr, &len, encoding );
+				if ( len == 1 )
+					(*text) += cArr[0];	// more efficient
+				else
+					text->append( cArr, len );
+			}
+		}
+	}
+	if ( p && *p )
+		p += strlen( endTag );
+	return ( p && *p ) ? p : 0;
+}
+
+#ifdef TIXML_USE_STL
+
+void TiXmlDocument::StreamIn( std::istream * in, TIXML_STRING * tag )
+{
+	// The basic issue with a document is that we don't know what we're
+	// streaming. Read something presumed to be a tag (and hope), then
+	// identify it, and call the appropriate stream method on the tag.
+	//
+	// This "pre-streaming" will never read the closing ">" so the
+	// sub-tag can orient itself.
+
+	if ( !StreamTo( in, '<', tag ) ) 
+	{
+		SetError( TIXML_ERROR_PARSING_EMPTY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return;
+	}
+
+	while ( in->good() )
+	{
+		int tagIndex = (int) tag->length();
+		while ( in->good() && in->peek() != '>' )
+		{
+			int c = in->get();
+			if ( c <= 0 )
+			{
+				SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+				break;
+			}
+			(*tag) += (char) c;
+		}
+
+		if ( in->good() )
+		{
+			// We now have something we presume to be a node of 
+			// some sort. Identify it, and call the node to
+			// continue streaming.
+			TiXmlNode* node = Identify( tag->c_str() + tagIndex, TIXML_DEFAULT_ENCODING );
+
+			if ( node )
+			{
+				node->StreamIn( in, tag );
+				bool isElement = node->ToElement() != 0;
+				delete node;
+				node = 0;
+
+				// If this is the root element, we're done. Parsing will be
+				// done by the >> operator.
+				if ( isElement )
+				{
+					return;
+				}
+			}
+			else
+			{
+				SetError( TIXML_ERROR, 0, 0, TIXML_ENCODING_UNKNOWN );
+				return;
+			}
+		}
+	}
+	// We should have returned sooner.
+	SetError( TIXML_ERROR, 0, 0, TIXML_ENCODING_UNKNOWN );
+}
+
+#endif
+
+const char* TiXmlDocument::Parse( const char* p, TiXmlParsingData* prevData, TiXmlEncoding encoding )
+{
+	ClearError();
+
+	// Parse away, at the document level. Since a document
+	// contains nothing but other tags, most of what happens
+	// here is skipping white space.
+	if ( !p || !*p )
+	{
+		SetError( TIXML_ERROR_DOCUMENT_EMPTY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return 0;
+	}
+
+	// Note that, for a document, this needs to come
+	// before the while space skip, so that parsing
+	// starts from the pointer we are given.
+	location.Clear();
+	if ( prevData )
+	{
+		location.row = prevData->cursor.row;
+		location.col = prevData->cursor.col;
+	}
+	else
+	{
+		location.row = 0;
+		location.col = 0;
+	}
+	TiXmlParsingData data( p, TabSize(), location.row, location.col );
+	location = data.Cursor();
+
+	if ( encoding == TIXML_ENCODING_UNKNOWN )
+	{
+		// Check for the Microsoft UTF-8 lead bytes.
+		const unsigned char* pU = (const unsigned char*)p;
+		if (	*(pU+0) && *(pU+0) == TIXML_UTF_LEAD_0
+			 && *(pU+1) && *(pU+1) == TIXML_UTF_LEAD_1
+			 && *(pU+2) && *(pU+2) == TIXML_UTF_LEAD_2 )
+		{
+			encoding = TIXML_ENCODING_UTF8;
+			useMicrosoftBOM = true;
+		}
+	}
+
+    p = SkipWhiteSpace( p, encoding );
+	if ( !p )
+	{
+		SetError( TIXML_ERROR_DOCUMENT_EMPTY, 0, 0, TIXML_ENCODING_UNKNOWN );
+		return 0;
+	}
+
+	while ( p && *p )
+	{
+		TiXmlNode* node = Identify( p, encoding );
+		if ( node )
+		{
+			p = node->Parse( p, &data, encoding );
+			LinkEndChild( node );
+		}
+		else
+		{
+			break;
+		}
+
+		// Did we get encoding info?
+		if (    encoding == TIXML_ENCODING_UNKNOWN
+			 && node->ToDeclaration() )
+		{
+			TiXmlDeclaration* dec = node->ToDeclaration();
+			const char* enc = dec->Encoding();
+			assert( enc );
+
+			if ( *enc == 0 )
+				encoding = TIXML_ENCODING_UTF8;
+			else if ( StringEqual( enc, "UTF-8", true, TIXML_ENCODING_UNKNOWN ) )
+				encoding = TIXML_ENCODING_UTF8;
+			else if ( StringEqual( enc, "UTF8", true, TIXML_ENCODING_UNKNOWN ) )
+				encoding = TIXML_ENCODING_UTF8;	// incorrect, but be nice
+			else 
+				encoding = TIXML_ENCODING_LEGACY;
+		}
+
+		p = SkipWhiteSpace( p, encoding );
+	}
+
+	// Was this empty?
+	if ( !firstChild ) {
+		SetError( TIXML_ERROR_DOCUMENT_EMPTY, 0, 0, encoding );
+		return 0;
+	}
+
+	// All is well.
+	return p;
+}
+
+void TiXmlDocument::SetError( int err, const char* pError, TiXmlParsingData* data, TiXmlEncoding encoding )
+{	
+	// The first error in a chain is more accurate - don't set again!
+	if ( error )
+		return;
+
+	assert( err > 0 && err < TIXML_ERROR_STRING_COUNT );
+	error   = true;
+	errorId = err;
+	errorDesc = errorString[ errorId ];
+
+	errorLocation.Clear();
+	if ( pError && data )
+	{
+		data->Stamp( pError, encoding );
+		errorLocation = data->Cursor();
+	}
+}
+
+
+TiXmlNode* TiXmlNode::Identify( const char* p, TiXmlEncoding encoding )
+{
+	TiXmlNode* returnNode = 0;
+
+	p = SkipWhiteSpace( p, encoding );
+	if( !p || !*p || *p != '<' )
+	{
+		return 0;
+	}
+
+	p = SkipWhiteSpace( p, encoding );
+
+	if ( !p || !*p )
+	{
+		return 0;
+	}
+
+	// What is this thing? 
+	// - Elements start with a letter or underscore, but xml is reserved.
+	// - Comments: <!--
+	// - Decleration: <?xml
+	// - Everthing else is unknown to tinyxml.
+	//
+
+	const char* xmlHeader = { "<?xml" };
+	const char* commentHeader = { "<!--" };
+	const char* dtdHeader = { "<!" };
+	const char* cdataHeader = { "<![CDATA[" };
+
+	if ( StringEqual( p, xmlHeader, true, encoding ) )
+	{
+		#ifdef DEBUG_PARSER
+			TIXML_LOG( "XML parsing Declaration\n" );
+		#endif
+		returnNode = new TiXmlDeclaration();
+	}
+	else if ( StringEqual( p, commentHeader, false, encoding ) )
+	{
+		#ifdef DEBUG_PARSER
+			TIXML_LOG( "XML parsing Comment\n" );
+		#endif
+		returnNode = new TiXmlComment();
+	}
+	else if ( StringEqual( p, cdataHeader, false, encoding ) )
+	{
+		#ifdef DEBUG_PARSER
+			TIXML_LOG( "XML parsing CDATA\n" );
+		#endif
+		TiXmlText* text = new TiXmlText( "" );
+		text->SetCDATA( true );
+		returnNode = text;
+	}
+	else if ( StringEqual( p, dtdHeader, false, encoding ) )
+	{
+		#ifdef DEBUG_PARSER
+			TIXML_LOG( "XML parsing Unknown(1)\n" );
+		#endif
+		returnNode = new TiXmlUnknown();
+	}
+	else if (    IsAlpha( *(p+1), encoding )
+			  || *(p+1) == '_' )
+	{
+		#ifdef DEBUG_PARSER
+			TIXML_LOG( "XML parsing Element\n" );
+		#endif
+		returnNode = new TiXmlElement( "" );
+	}
+	else
+	{
+		#ifdef DEBUG_PARSER
+			TIXML_LOG( "XML parsing Unknown(2)\n" );
+		#endif
+		returnNode = new TiXmlUnknown();
+	}
+
+	if ( returnNode )
+	{
+		// Set the parent, so it can report errors
+		returnNode->parent = this;
+	}
+	return returnNode;
+}
+
+#ifdef TIXML_USE_STL
+
+void TiXmlElement::StreamIn (std::istream * in, TIXML_STRING * tag)
+{
+	// We're called with some amount of pre-parsing. That is, some of "this"
+	// element is in "tag". Go ahead and stream to the closing ">"
+	while( in->good() )
+	{
+		int c = in->get();
+		if ( c <= 0 )
+		{
+			TiXmlDocument* document = GetDocument();
+			if ( document )
+				document->SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+			return;
+		}
+		(*tag) += (char) c ;
+		
+		if ( c == '>' )
+			break;
+	}
+
+	if ( tag->length() < 3 ) return;
+
+	// Okay...if we are a "/>" tag, then we're done. We've read a complete tag.
+	// If not, identify and stream.
+
+	if (    tag->at( tag->length() - 1 ) == '>' 
+		 && tag->at( tag->length() - 2 ) == '/' )
+	{
+		// All good!
+		return;
+	}
+	else if ( tag->at( tag->length() - 1 ) == '>' )
+	{
+		// There is more. Could be:
+		//		text
+		//		cdata text (which looks like another node)
+		//		closing tag
+		//		another node.
+		for ( ;; )
+		{
+			StreamWhiteSpace( in, tag );
+
+			// Do we have text?
+			if ( in->good() && in->peek() != '<' ) 
+			{
+				// Yep, text.
+				TiXmlText text( "" );
+				text.StreamIn( in, tag );
+
+				// What follows text is a closing tag or another node.
+				// Go around again and figure it out.
+				continue;
+			}
+
+			// We now have either a closing tag...or another node.
+			// We should be at a "<", regardless.
+			if ( !in->good() ) return;
+			assert( in->peek() == '<' );
+			int tagIndex = (int) tag->length();
+
+			bool closingTag = false;
+			bool firstCharFound = false;
+
+			for( ;; )
+			{
+				if ( !in->good() )
+					return;
+
+				int c = in->peek();
+				if ( c <= 0 )
+				{
+					TiXmlDocument* document = GetDocument();
+					if ( document )
+						document->SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+					return;
+				}
+				
+				if ( c == '>' )
+					break;
+
+				*tag += (char) c;
+				in->get();
+
+				// Early out if we find the CDATA id.
+				if ( c == '[' && tag->size() >= 9 )
+				{
+					size_t len = tag->size();
+					const char* start = tag->c_str() + len - 9;
+					if ( strcmp( start, "<![CDATA[" ) == 0 ) {
+						assert( !closingTag );
+						break;
+					}
+				}
+
+				if ( !firstCharFound && c != '<' && !IsWhiteSpace( c ) )
+				{
+					firstCharFound = true;
+					if ( c == '/' )
+						closingTag = true;
+				}
+			}
+			// If it was a closing tag, then read in the closing '>' to clean up the input stream.
+			// If it was not, the streaming will be done by the tag.
+			if ( closingTag )
+			{
+				if ( !in->good() )
+					return;
+
+				int c = in->get();
+				if ( c <= 0 )
+				{
+					TiXmlDocument* document = GetDocument();
+					if ( document )
+						document->SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+					return;
+				}
+				assert( c == '>' );
+				*tag += (char) c;
+
+				// We are done, once we've found our closing tag.
+				return;
+			}
+			else
+			{
+				// If not a closing tag, id it, and stream.
+				const char* tagloc = tag->c_str() + tagIndex;
+				TiXmlNode* node = Identify( tagloc, TIXML_DEFAULT_ENCODING );
+				if ( !node )
+					return;
+				node->StreamIn( in, tag );
+				delete node;
+				node = 0;
+
+				// No return: go around from the beginning: text, closing tag, or node.
+			}
+		}
+	}
+}
+#endif
+
+const char* TiXmlElement::Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding )
+{
+	p = SkipWhiteSpace( p, encoding );
+	TiXmlDocument* document = GetDocument();
+
+	if ( !p || !*p )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_PARSING_ELEMENT, 0, 0, encoding );
+		return 0;
+	}
+
+	if ( data )
+	{
+		data->Stamp( p, encoding );
+		location = data->Cursor();
+	}
+
+	if ( *p != '<' )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_PARSING_ELEMENT, p, data, encoding );
+		return 0;
+	}
+
+	p = SkipWhiteSpace( p+1, encoding );
+
+	// Read the name.
+	const char* pErr = p;
+
+    p = ReadName( p, &value, encoding );
+	if ( !p || !*p )
+	{
+		if ( document )	document->SetError( TIXML_ERROR_FAILED_TO_READ_ELEMENT_NAME, pErr, data, encoding );
+		return 0;
+	}
+
+    TIXML_STRING endTag ("</");
+	endTag += value;
+
+	// Check for and read attributes. Also look for an empty
+	// tag or an end tag.
+	while ( p && *p )
+	{
+		pErr = p;
+		p = SkipWhiteSpace( p, encoding );
+		if ( !p || !*p )
+		{
+			if ( document ) document->SetError( TIXML_ERROR_READING_ATTRIBUTES, pErr, data, encoding );
+			return 0;
+		}
+		if ( *p == '/' )
+		{
+			++p;
+			// Empty tag.
+			if ( *p  != '>' )
+			{
+				if ( document ) document->SetError( TIXML_ERROR_PARSING_EMPTY, p, data, encoding );		
+				return 0;
+			}
+			return (p+1);
+		}
+		else if ( *p == '>' )
+		{
+			// Done with attributes (if there were any.)
+			// Read the value -- which can include other
+			// elements -- read the end tag, and return.
+			++p;
+			p = ReadValue( p, data, encoding );		// Note this is an Element method, and will set the error if one happens.
+			if ( !p || !*p ) {
+				// We were looking for the end tag, but found nothing.
+				// Fix for [ 1663758 ] Failure to report error on bad XML
+				if ( document ) document->SetError( TIXML_ERROR_READING_END_TAG, p, data, encoding );
+				return 0;
+			}
+
+			// We should find the end tag now
+			// note that:
+			// </foo > and
+			// </foo> 
+			// are both valid end tags.
+			if ( StringEqual( p, endTag.c_str(), false, encoding ) )
+			{
+				p += endTag.length();
+				p = SkipWhiteSpace( p, encoding );
+				if ( p && *p && *p == '>' ) {
+					++p;
+					return p;
+				}
+				if ( document ) document->SetError( TIXML_ERROR_READING_END_TAG, p, data, encoding );
+				return 0;
+			}
+			else
+			{
+				if ( document ) document->SetError( TIXML_ERROR_READING_END_TAG, p, data, encoding );
+				return 0;
+			}
+		}
+		else
+		{
+			// Try to read an attribute:
+			TiXmlAttribute* attrib = new TiXmlAttribute();
+			if ( !attrib )
+			{
+				return 0;
+			}
+
+			attrib->SetDocument( document );
+			pErr = p;
+			p = attrib->Parse( p, data, encoding );
+
+			if ( !p || !*p )
+			{
+				if ( document ) document->SetError( TIXML_ERROR_PARSING_ELEMENT, pErr, data, encoding );
+				delete attrib;
+				return 0;
+			}
+
+			// Handle the strange case of double attributes:
+			#ifdef TIXML_USE_STL
+			TiXmlAttribute* node = attributeSet.Find( attrib->NameTStr() );
+			#else
+			TiXmlAttribute* node = attributeSet.Find( attrib->Name() );
+			#endif
+			if ( node )
+			{
+				if ( document ) document->SetError( TIXML_ERROR_PARSING_ELEMENT, pErr, data, encoding );
+				delete attrib;
+				return 0;
+			}
+
+			attributeSet.Add( attrib );
+		}
+	}
+	return p;
+}
+
+
+const char* TiXmlElement::ReadValue( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding )
+{
+	TiXmlDocument* document = GetDocument();
+
+	// Read in text and elements in any order.
+	const char* pWithWhiteSpace = p;
+	p = SkipWhiteSpace( p, encoding );
+
+	while ( p && *p )
+	{
+		if ( *p != '<' )
+		{
+			// Take what we have, make a text element.
+			TiXmlText* textNode = new TiXmlText( "" );
+
+			if ( !textNode )
+			{
+			    return 0;
+			}
+
+			if ( TiXmlBase::IsWhiteSpaceCondensed() )
+			{
+				p = textNode->Parse( p, data, encoding );
+			}
+			else
+			{
+				// Special case: we want to keep the white space
+				// so that leading spaces aren't removed.
+				p = textNode->Parse( pWithWhiteSpace, data, encoding );
+			}
+
+			if ( !textNode->Blank() )
+				LinkEndChild( textNode );
+			else
+				delete textNode;
+		} 
+		else 
+		{
+			// We hit a '<'
+			// Have we hit a new element or an end tag? This could also be
+			// a TiXmlText in the "CDATA" style.
+			if ( StringEqual( p, "</", false, encoding ) )
+			{
+				return p;
+			}
+			else
+			{
+				TiXmlNode* node = Identify( p, encoding );
+				if ( node )
+				{
+					p = node->Parse( p, data, encoding );
+					LinkEndChild( node );
+				}				
+				else
+				{
+					return 0;
+				}
+			}
+		}
+		pWithWhiteSpace = p;
+		p = SkipWhiteSpace( p, encoding );
+	}
+
+	if ( !p )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_READING_ELEMENT_VALUE, 0, 0, encoding );
+	}	
+	return p;
+}
+
+
+#ifdef TIXML_USE_STL
+void TiXmlUnknown::StreamIn( std::istream * in, TIXML_STRING * tag )
+{
+	while ( in->good() )
+	{
+		int c = in->get();	
+		if ( c <= 0 )
+		{
+			TiXmlDocument* document = GetDocument();
+			if ( document )
+				document->SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+			return;
+		}
+		(*tag) += (char) c;
+
+		if ( c == '>' )
+		{
+			// All is well.
+			return;		
+		}
+	}
+}
+#endif
+
+
+const char* TiXmlUnknown::Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding )
+{
+	TiXmlDocument* document = GetDocument();
+	p = SkipWhiteSpace( p, encoding );
+
+	if ( data )
+	{
+		data->Stamp( p, encoding );
+		location = data->Cursor();
+	}
+	if ( !p || !*p || *p != '<' )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_PARSING_UNKNOWN, p, data, encoding );
+		return 0;
+	}
+	++p;
+    value = "";
+
+	while ( p && *p && *p != '>' )
+	{
+		value += *p;
+		++p;
+	}
+
+	if ( !p )
+	{
+		if ( document )	
+			document->SetError( TIXML_ERROR_PARSING_UNKNOWN, 0, 0, encoding );
+	}
+	if ( p && *p == '>' )
+		return p+1;
+	return p;
+}
+
+#ifdef TIXML_USE_STL
+void TiXmlComment::StreamIn( std::istream * in, TIXML_STRING * tag )
+{
+	while ( in->good() )
+	{
+		int c = in->get();	
+		if ( c <= 0 )
+		{
+			TiXmlDocument* document = GetDocument();
+			if ( document )
+				document->SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+			return;
+		}
+
+		(*tag) += (char) c;
+
+		if ( c == '>' 
+			 && tag->at( tag->length() - 2 ) == '-'
+			 && tag->at( tag->length() - 3 ) == '-' )
+		{
+			// All is well.
+			return;		
+		}
+	}
+}
+#endif
+
+
+const char* TiXmlComment::Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding )
+{
+	TiXmlDocument* document = GetDocument();
+	value = "";
+
+	p = SkipWhiteSpace( p, encoding );
+
+	if ( data )
+	{
+		data->Stamp( p, encoding );
+		location = data->Cursor();
+	}
+	const char* startTag = "<!--";
+	const char* endTag   = "-->";
+
+	if ( !StringEqual( p, startTag, false, encoding ) )
+	{
+		if ( document )
+			document->SetError( TIXML_ERROR_PARSING_COMMENT, p, data, encoding );
+		return 0;
+	}
+	p += strlen( startTag );
+
+	// [ 1475201 ] TinyXML parses entities in comments
+	// Oops - ReadText doesn't work, because we don't want to parse the entities.
+	// p = ReadText( p, &value, false, endTag, false, encoding );
+	//
+	// from the XML spec:
+	/*
+	 [Definition: Comments may appear anywhere in a document outside other markup; in addition, 
+	              they may appear within the document type declaration at places allowed by the grammar. 
+				  They are not part of the document's character data; an XML processor MAY, but need not, 
+				  make it possible for an application to retrieve the text of comments. For compatibility, 
+				  the string "--" (double-hyphen) MUST NOT occur within comments.] Parameter entity 
+				  references MUST NOT be recognized within comments.
+
+				  An example of a comment:
+
+				  <!-- declarations for <head> & <body> -->
+	*/
+
+    value = "";
+	// Keep all the white space.
+	while (	p && *p && !StringEqual( p, endTag, false, encoding ) )
+	{
+		value.append( p, 1 );
+		++p;
+	}
+	if ( p && *p ) 
+		p += strlen( endTag );
+
+	return p;
+}
+
+
+const char* TiXmlAttribute::Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding )
+{
+	p = SkipWhiteSpace( p, encoding );
+	if ( !p || !*p ) return 0;
+
+	if ( data )
+	{
+		data->Stamp( p, encoding );
+		location = data->Cursor();
+	}
+	// Read the name, the '=' and the value.
+	const char* pErr = p;
+	p = ReadName( p, &name, encoding );
+	if ( !p || !*p )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_READING_ATTRIBUTES, pErr, data, encoding );
+		return 0;
+	}
+	p = SkipWhiteSpace( p, encoding );
+	if ( !p || !*p || *p != '=' )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_READING_ATTRIBUTES, p, data, encoding );
+		return 0;
+	}
+
+	++p;	// skip '='
+	p = SkipWhiteSpace( p, encoding );
+	if ( !p || !*p )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_READING_ATTRIBUTES, p, data, encoding );
+		return 0;
+	}
+	
+	const char* end;
+	const char SINGLE_QUOTE = '\'';
+	const char DOUBLE_QUOTE = '\"';
+
+	if ( *p == SINGLE_QUOTE )
+	{
+		++p;
+		end = "\'";		// single quote in string
+		p = ReadText( p, &value, false, end, false, encoding );
+	}
+	else if ( *p == DOUBLE_QUOTE )
+	{
+		++p;
+		end = "\"";		// double quote in string
+		p = ReadText( p, &value, false, end, false, encoding );
+	}
+	else
+	{
+		// All attribute values should be in single or double quotes.
+		// But this is such a common error that the parser will try
+		// its best, even without them.
+		value = "";
+		while (    p && *p											// existence
+				&& !IsWhiteSpace( *p )								// whitespace
+				&& *p != '/' && *p != '>' )							// tag end
+		{
+			if ( *p == SINGLE_QUOTE || *p == DOUBLE_QUOTE ) {
+				// [ 1451649 ] Attribute values with trailing quotes not handled correctly
+				// We did not have an opening quote but seem to have a 
+				// closing one. Give up and throw an error.
+				if ( document ) document->SetError( TIXML_ERROR_READING_ATTRIBUTES, p, data, encoding );
+				return 0;
+			}
+			value += *p;
+			++p;
+		}
+	}
+	return p;
+}
+
+#ifdef TIXML_USE_STL
+void TiXmlText::StreamIn( std::istream * in, TIXML_STRING * tag )
+{
+	while ( in->good() )
+	{
+		int c = in->peek();	
+		if ( !cdata && (c == '<' ) ) 
+		{
+			return;
+		}
+		if ( c <= 0 )
+		{
+			TiXmlDocument* document = GetDocument();
+			if ( document )
+				document->SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+			return;
+		}
+
+		(*tag) += (char) c;
+		in->get();	// "commits" the peek made above
+
+		if ( cdata && c == '>' && tag->size() >= 3 ) {
+			size_t len = tag->size();
+			if ( (*tag)[len-2] == ']' && (*tag)[len-3] == ']' ) {
+				// terminator of cdata.
+				return;
+			}
+		}    
+	}
+}
+#endif
+
+const char* TiXmlText::Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding encoding )
+{
+	value = "";
+	TiXmlDocument* document = GetDocument();
+
+	if ( data )
+	{
+		data->Stamp( p, encoding );
+		location = data->Cursor();
+	}
+
+	const char* const startTag = "<![CDATA[";
+	const char* const endTag   = "]]>";
+
+	if ( cdata || StringEqual( p, startTag, false, encoding ) )
+	{
+		cdata = true;
+
+		if ( !StringEqual( p, startTag, false, encoding ) )
+		{
+			if ( document )
+				document->SetError( TIXML_ERROR_PARSING_CDATA, p, data, encoding );
+			return 0;
+		}
+		p += strlen( startTag );
+
+		// Keep all the white space, ignore the encoding, etc.
+		while (	   p && *p
+				&& !StringEqual( p, endTag, false, encoding )
+			  )
+		{
+			value += *p;
+			++p;
+		}
+
+		TIXML_STRING dummy; 
+		p = ReadText( p, &dummy, false, endTag, false, encoding );
+		return p;
+	}
+	else
+	{
+		bool ignoreWhite = true;
+
+		const char* end = "<";
+		p = ReadText( p, &value, ignoreWhite, end, false, encoding );
+		if ( p && *p )
+			return p-1;	// don't truncate the '<'
+		return 0;
+	}
+}
+
+#ifdef TIXML_USE_STL
+void TiXmlDeclaration::StreamIn( std::istream * in, TIXML_STRING * tag )
+{
+	while ( in->good() )
+	{
+		int c = in->get();
+		if ( c <= 0 )
+		{
+			TiXmlDocument* document = GetDocument();
+			if ( document )
+				document->SetError( TIXML_ERROR_EMBEDDED_NULL, 0, 0, TIXML_ENCODING_UNKNOWN );
+			return;
+		}
+		(*tag) += (char) c;
+
+		if ( c == '>' )
+		{
+			// All is well.
+			return;
+		}
+	}
+}
+#endif
+
+const char* TiXmlDeclaration::Parse( const char* p, TiXmlParsingData* data, TiXmlEncoding _encoding )
+{
+	p = SkipWhiteSpace( p, _encoding );
+	// Find the beginning, find the end, and look for
+	// the stuff in-between.
+	TiXmlDocument* document = GetDocument();
+	if ( !p || !*p || !StringEqual( p, "<?xml", true, _encoding ) )
+	{
+		if ( document ) document->SetError( TIXML_ERROR_PARSING_DECLARATION, 0, 0, _encoding );
+		return 0;
+	}
+	if ( data )
+	{
+		data->Stamp( p, _encoding );
+		location = data->Cursor();
+	}
+	p += 5;
+
+	version = "";
+	encoding = "";
+	standalone = "";
+
+	while ( p && *p )
+	{
+		if ( *p == '>' )
+		{
+			++p;
+			return p;
+		}
+
+		p = SkipWhiteSpace( p, _encoding );
+		if ( StringEqual( p, "version", true, _encoding ) )
+		{
+			TiXmlAttribute attrib;
+			p = attrib.Parse( p, data, _encoding );		
+			version = attrib.Value();
+		}
+		else if ( StringEqual( p, "encoding", true, _encoding ) )
+		{
+			TiXmlAttribute attrib;
+			p = attrib.Parse( p, data, _encoding );		
+			encoding = attrib.Value();
+		}
+		else if ( StringEqual( p, "standalone", true, _encoding ) )
+		{
+			TiXmlAttribute attrib;
+			p = attrib.Parse( p, data, _encoding );		
+			standalone = attrib.Value();
+		}
+		else
+		{
+			// Read over whatever it is.
+			while( p && *p && *p != '>' && !IsWhiteSpace( *p ) )
+				++p;
+		}
+	}
+	return 0;
+}
+
+bool TiXmlText::Blank() const
+{
+	for ( unsigned i=0; i<value.length(); i++ )
+		if ( !IsWhiteSpace( value[i] ) )
+			return false;
+	return true;
+}
+
diff --git a/sfntly/cpp/src/test/verify_glyf.cc b/sfntly/cpp/src/test/verify_glyf.cc
new file mode 100644
index 0000000..abfe1ab
--- /dev/null
+++ b/sfntly/cpp/src/test/verify_glyf.cc
@@ -0,0 +1,59 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/table/truetype/glyph_table.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+// We spot check only glyph id 33.
+const int32_t GLYPH33_OFFSET = 0xAC8;
+const int32_t GLYPH33_LENGTH = 40;
+const int32_t GLYPH33_XMIN = 92;
+const int32_t GLYPH33_YMIN = 20;
+const int32_t GLYPH33_XMAX = 797;
+const int32_t GLYPH33_YMAX = 1235;
+
+// TODO(arthurhsu): Tuffy does not have composite glyphs.  Need better testing.
+static bool VerifyGLYF(Table* table) {
+  GlyphTablePtr glyf_table = down_cast<GlyphTable*>(table);
+  if (glyf_table == NULL) {
+    return false;
+  }
+
+  GlyphPtr glyf;
+  glyf.Attach(glyf_table->GetGlyph(GLYPH33_OFFSET, GLYPH33_LENGTH));
+  if (glyf == NULL) {
+    return false;
+  }
+
+  EXPECT_EQ(glyf->XMin(), GLYPH33_XMIN);
+  EXPECT_EQ(glyf->YMin(), GLYPH33_YMIN);
+  EXPECT_EQ(glyf->XMax(), GLYPH33_XMAX);
+  EXPECT_EQ(glyf->YMax(), GLYPH33_YMAX);
+
+  return true;
+}
+
+bool VerifyGLYF(Table* original, Table* target) {
+  EXPECT_TRUE(VerifyGLYF(original));
+  EXPECT_TRUE(VerifyGLYF(target));
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/verify_hhea.cc b/sfntly/cpp/src/test/verify_hhea.cc
new file mode 100644
index 0000000..81ddb58
--- /dev/null
+++ b/sfntly/cpp/src/test/verify_hhea.cc
@@ -0,0 +1,63 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/math/fixed1616.h"
+#include "sfntly/table/core/horizontal_header_table.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+const int32_t HHEA_ASCENDER = 2023;
+const int32_t HHEA_DESCENDER = -648;
+const int32_t HHEA_LINE_GAP = 93;
+const int32_t HHEA_ADVANCE_WIDTH_MAX = 2753;
+const int32_t HHEA_MIN_LSB = -968;
+const int32_t HHEA_MIN_RSB = -411;
+const int32_t HHEA_X_MAX_EXTENT = 2628;
+const int32_t HHEA_METRIC_DATA_FORMAT = 0;
+const int32_t HHEA_NUM_METRICS = 1499;
+
+static bool VerifyHHEA(Table* table) {
+  HorizontalHeaderTablePtr hhea = down_cast<HorizontalHeaderTable*>(table);
+  if (hhea == NULL) {
+    return false;
+  }
+
+  EXPECT_EQ(hhea->TableVersion(), Fixed1616::Fixed(1, 0));
+  EXPECT_EQ(hhea->Ascender(), HHEA_ASCENDER);
+  EXPECT_EQ(hhea->Descender(), HHEA_DESCENDER);
+  EXPECT_EQ(hhea->AdvanceWidthMax(), HHEA_ADVANCE_WIDTH_MAX);
+  EXPECT_EQ(hhea->MinLeftSideBearing(), HHEA_MIN_LSB);
+  EXPECT_EQ(hhea->MinRightSideBearing(), HHEA_MIN_RSB);
+  EXPECT_EQ(hhea->XMaxExtent(), HHEA_X_MAX_EXTENT);
+  // TODO(arthurhsu): CaretSlopeRise() not tested
+  // TODO(arthurhsu): CaretSlopeRun() not tested
+  // TODO(arthurhsu): CaretOffset() not tested
+  EXPECT_EQ(hhea->MetricDataFormat(), HHEA_METRIC_DATA_FORMAT);
+  EXPECT_EQ(hhea->NumberOfHMetrics(), HHEA_NUM_METRICS);
+
+  return true;
+}
+
+bool VerifyHHEA(Table* original, Table* target) {
+  EXPECT_TRUE(VerifyHHEA(original));
+  EXPECT_TRUE(VerifyHHEA(target));
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/verify_hmtx.cc b/sfntly/cpp/src/test/verify_hmtx.cc
new file mode 100644
index 0000000..d37bba9
--- /dev/null
+++ b/sfntly/cpp/src/test/verify_hmtx.cc
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/table/core/horizontal_metrics_table.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+const int32_t HMTX_ENTRIES_COUNT = 1499;
+const int32_t HMTX_LSB_COUNT = 3;
+
+struct HmtxEntry {
+  int32_t advance_width_;
+  int32_t lsb_;
+
+  HmtxEntry(int32_t advance_width, int32_t lsb)
+      : advance_width_(advance_width), lsb_(lsb) {}
+};
+
+const HmtxEntry HMTX_ENTRIES[] = {
+    HmtxEntry(748, 68),  // 0
+    HmtxEntry(0, 0),  // 1
+    HmtxEntry(682, 0),  // 2
+    HmtxEntry(616, 0),  // 3
+    HmtxEntry(421, 103),  // 4
+    HmtxEntry(690, 129),  // 5
+    HmtxEntry(1589, 129),  // 6
+    HmtxEntry(1017, 25),  // 7
+    HmtxEntry(1402, 104),  // 8
+    HmtxEntry(1241, 100),  // 9
+};
+const int32_t NUM_HMTX_ENTRIES = 10;
+
+static bool VerifyHMTX(Table* table) {
+  HorizontalMetricsTablePtr hmtx = down_cast<HorizontalMetricsTable*>(table);
+  if (hmtx == NULL) {
+    return false;
+  }
+
+  EXPECT_EQ(hmtx->NumberOfHMetrics(), HMTX_ENTRIES_COUNT);
+  EXPECT_EQ(hmtx->NumberOfLSBs(), HMTX_LSB_COUNT);
+
+  for (int32_t i = 0; i < NUM_HMTX_ENTRIES; ++i) {
+    EXPECT_EQ(hmtx->AdvanceWidth(i), HMTX_ENTRIES[i].advance_width_);
+    EXPECT_EQ(hmtx->LeftSideBearing(i), HMTX_ENTRIES[i].lsb_);
+  }
+
+  // No such element case.
+  EXPECT_EQ(hmtx->AdvanceWidth(HMTX_ENTRIES_COUNT),
+            HMTX_ENTRIES[0].advance_width_);
+  EXPECT_EQ(hmtx->LeftSideBearing(HMTX_ENTRIES_COUNT), HMTX_ENTRIES[0].lsb_);
+  return true;
+}
+
+bool VerifyHMTX(Table* original, Table* target) {
+  EXPECT_TRUE(VerifyHMTX(original));
+  EXPECT_TRUE(VerifyHMTX(target));
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/verify_loca.cc b/sfntly/cpp/src/test/verify_loca.cc
new file mode 100644
index 0000000..4a32928
--- /dev/null
+++ b/sfntly/cpp/src/test/verify_loca.cc
@@ -0,0 +1,62 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/table/truetype/loca_table.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+const int32_t LOCA_NUM_LOCAS = 1503;
+const int32_t LOCAS[] = {
+    0x00000,  // 0
+    0x00058,  // 1
+    0x00058,  // 2
+    0x00058,  // 3
+    0x00058,  // 4
+    0x000B8,  // 5
+    0x00138,  // 6
+    0x001A4,  // 7
+    0x0025C,  // 8
+    0x00328,  // 9
+    0x003B8,  // 10
+};
+const int32_t NUM_TEST_LOCAS = 11;
+
+static bool VerifyLOCA(Table* table) {
+  LocaTablePtr loca = down_cast<LocaTable*>(table);
+  if (loca == NULL) {
+    return false;
+  }
+
+  EXPECT_EQ(loca->NumLocas(), LOCA_NUM_LOCAS);
+  EXPECT_EQ(loca->num_glyphs(), LOCA_NUM_LOCAS - 1);
+
+  for (int32_t i = 0; i < NUM_TEST_LOCAS - 1; ++i) {
+    EXPECT_EQ(loca->GlyphOffset(i), LOCAS[i]);
+    EXPECT_EQ(loca->GlyphLength(i), LOCAS[i + 1] - LOCAS[i]);
+  }
+  return true;
+}
+
+bool VerifyLOCA(Table* original, Table* target) {
+  EXPECT_TRUE(VerifyLOCA(original));
+  EXPECT_TRUE(VerifyLOCA(target));
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/verify_maxp.cc b/sfntly/cpp/src/test/verify_maxp.cc
new file mode 100644
index 0000000..dcd776e
--- /dev/null
+++ b/sfntly/cpp/src/test/verify_maxp.cc
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/math/fixed1616.h"
+#include "sfntly/table/core/maximum_profile_table.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+const int32_t MAXP_NUM_GLYPHS = 1502;
+const int32_t MAXP_MAX_POINTS = 181;
+const int32_t MAXP_MAX_CONTOURS = 9;
+const int32_t MAXP_MAX_COMPOSITE_POINTS = 172;
+const int32_t MAXP_MAX_COMPOSITE_CONTOURS = 5;
+const int32_t MAXP_MAX_ZONES = 2;
+const int32_t MAXP_MAX_TWILIGHT_POINTS = 0;
+const int32_t MAXP_MAX_STORAGE = 1;
+const int32_t MAXP_MAX_FUNCTION_DEFS = 1;
+const int32_t MAXP_MAX_INSTR_DEFS = 0;
+const int32_t MAXP_MAX_STACK_ELEMENTS = 64;
+const int32_t MAXP_MAX_INSTR_SIZE = 46;
+const int32_t MAXP_MAX_COMPONENT_ELEMENTS = 4;
+const int32_t MAXP_MAX_COMPONENT_DEPTH = 3;
+
+static bool VerifyMAXP(Table* table) {
+  MaximumProfileTablePtr maxp = down_cast<MaximumProfileTable*>(table);
+  if (maxp == NULL) {
+    return false;
+  }
+
+  EXPECT_EQ(maxp->TableVersion(), Fixed1616::Fixed(1, 0));
+  EXPECT_EQ(maxp->NumGlyphs(), MAXP_NUM_GLYPHS);
+  EXPECT_EQ(maxp->MaxPoints(), MAXP_MAX_POINTS);
+  EXPECT_EQ(maxp->MaxContours(), MAXP_MAX_CONTOURS);
+  EXPECT_EQ(maxp->MaxCompositePoints(), MAXP_MAX_COMPOSITE_POINTS);
+  EXPECT_EQ(maxp->MaxCompositeContours(), MAXP_MAX_COMPOSITE_CONTOURS);
+  EXPECT_EQ(maxp->MaxZones(), MAXP_MAX_ZONES);
+  EXPECT_EQ(maxp->MaxTwilightPoints(), MAXP_MAX_TWILIGHT_POINTS);
+  EXPECT_EQ(maxp->MaxStorage(), MAXP_MAX_STORAGE);
+  EXPECT_EQ(maxp->MaxFunctionDefs(), MAXP_MAX_FUNCTION_DEFS);
+  // TODO(arthurhsu): maxInstructionDefs observed in Microsoft TTF report.
+  //                  Check with stuartg and see if this is a miss.
+  EXPECT_EQ(maxp->MaxStackElements(), MAXP_MAX_STACK_ELEMENTS);
+  EXPECT_EQ(maxp->MaxSizeOfInstructions(), MAXP_MAX_INSTR_SIZE);
+  EXPECT_EQ(maxp->MaxComponentElements(), MAXP_MAX_COMPONENT_ELEMENTS);
+  EXPECT_EQ(maxp->MaxComponentDepth(), MAXP_MAX_COMPONENT_DEPTH);
+
+  return true;
+}
+
+bool VerifyMAXP(Table* original, Table* target) {
+  EXPECT_TRUE(VerifyMAXP(original));
+  EXPECT_TRUE(VerifyMAXP(target));
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/verify_name.cc b/sfntly/cpp/src/test/verify_name.cc
new file mode 100644
index 0000000..e1101c0
--- /dev/null
+++ b/sfntly/cpp/src/test/verify_name.cc
@@ -0,0 +1,68 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/table/core/name_table.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+const int32_t NAME_FORMAT = 0;
+const int32_t NAME_COUNT = 75;
+const NameTable::NameEntryId NAME_IDS[] = {
+    NameTable::NameEntryId(1, 0, 0, 0),  // 0
+    NameTable::NameEntryId(1, 0, 0, 1),  // 1
+    NameTable::NameEntryId(1, 0, 0, 2),  // 2
+    NameTable::NameEntryId(1, 0, 0, 3),  // 3
+    NameTable::NameEntryId(1, 0, 0, 4),  // 4
+    NameTable::NameEntryId(1, 0, 0, 5),  // 5
+    NameTable::NameEntryId(1, 0, 0, 6),  // 6
+    NameTable::NameEntryId(1, 0, 0, 9),  // 7
+    NameTable::NameEntryId(1, 0, 0, 11),  // 8
+    NameTable::NameEntryId(1, 0, 0, 12),  // 9
+};
+const int32_t NAME_IDS_TEST = 10;
+
+static bool VerifyNAME(Table* table) {
+  // TODO(arthurhsu): Better testing can be done here.  Right now we just
+  //                  iterate through the entries and get entry ids.
+  NameTablePtr name = down_cast<NameTable*>(table);
+  if (name == NULL) {
+    return false;
+  }
+
+  EXPECT_EQ(name->Format(), NAME_FORMAT);
+  EXPECT_EQ(name->NameCount(), NAME_COUNT);
+  fprintf(stderr, "checking name entry: ");
+  for (int32_t i = 0; i < NAME_IDS_TEST; ++i) {
+    fprintf(stderr, "%d ", i);
+    EXPECT_EQ(name->PlatformId(i), NAME_IDS[i].platform_id());
+    EXPECT_EQ(name->EncodingId(i), NAME_IDS[i].encoding_id());
+    EXPECT_EQ(name->LanguageId(i), NAME_IDS[i].language_id());
+    EXPECT_EQ(name->NameId(i), NAME_IDS[i].name_id());
+  }
+  fprintf(stderr, "\n");
+  return true;
+}
+
+bool VerifyNAME(Table* original, Table* target) {
+  EXPECT_TRUE(VerifyNAME(original));
+  EXPECT_TRUE(VerifyNAME(target));
+  return true;
+}
+
+}  // namespace sfntly
diff --git a/sfntly/cpp/src/test/verify_os2.cc b/sfntly/cpp/src/test/verify_os2.cc
new file mode 100644
index 0000000..4897e87
--- /dev/null
+++ b/sfntly/cpp/src/test/verify_os2.cc
@@ -0,0 +1,125 @@
+/*
+ * Copyright 2011 Google Inc. All Rights Reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "gtest/gtest.h"
+#include "sfntly/font.h"
+#include "sfntly/table/core/os2_table.h"
+#include "test/serialization_test.h"
+
+namespace sfntly {
+
+const int32_t OS2_VERSION = 1;
+const int32_t OS2_XAVG_CHAR_WIDTH = 863;
+const int32_t OS2_US_WEIGHT_CLASS = 500;
+const int32_t OS2_US_WIDTH_CLASS = 5;
+const int32_t OS2_FS_TYPE = 0;
+const int32_t OS2_YSUBS_XSIZE = 0;
+const int32_t OS2_YSUBS_YSIZE = 2;
+const int32_t OS2_YSUBS_XOFFSET = -16560;
+const int32_t OS2_YSUBS_YOFFSET = 0;
+const int32_t OS2_YSUPS_XSIZE = -25944;
+const int32_t OS2_YSUPS_YSIZE = -27176;
+const int32_t OS2_YSUPS_XOFFSET = -16376;
+const int32_t OS2_YSUPS_YOFFSET = 1;
+const int32_t OS2_YSTRIKEOUT_SIZE = 12312;
+const int32_t OS2_YSTRIKEOUT_POS = -16224;
+const int32_t OS2_SFAMILY_CLASS = 0;
+const byte_t OS2_PANOSE[] = { 2, 11, 6, 3, 6, 1, 0, 0, 0, 0 };
+const int64_t OS2_UL_UNICODE_RANGE1 = 0xE00002FFL;
+const int64_t OS2_UL_UNICODE_RANGE2 = 0x520020FBL;
+const int64_t OS2_UL_UNICODE_RANGE3 = 0L;
+const int64_t OS2_UL_UNICODE_RANGE4 = 0L;
+const byte_t OS2_ACH_VEND_ID[] = { 'P', 'f', 'E', 'd' };
+const int32_t OS2_FS_SELECTION = 0x0040;
+const int32_t OS2_US_FIRST_CHAR_IDX = 0x0020;
+const int32_t OS2_US_LAST_CHAR_IDX = 0xFFFF;
+const int32_t OS2_STYPO_ASCENDER = 1597;
+const int32_t OS2_STYPO_DESCENDER = -451;
+const int32_t OS2_STYPO_LINE_GAP = 0;
+const int32_t OS2_US_WIN_ASCENT = 2023;
+const int32_t OS2_US_WIN_DESCENT = 648;
+const int64_t OS2_UL_CODE_PAGE_RANGE1 = 0x2000019FL;
+const int64_t OS2_UL_CODE_PAGE_RANGE2 = 0x00000000L;
+
+static bool VerifyOS_2(Table* table) {
+  OS2TablePtr os2 = down_cast<OS2Table*>(table);
+  if (os2 == NULL) {
+    return false;
+  }
+
+  EXPECT_EQ(os2->TableVersion(), OS2_VERSION);
+  EXPECT_EQ(os2->XAvgCharWidth(), OS2_XAVG_CHAR_WIDTH);
+  EXPECT_EQ(os2->UsWeightClass(), OS2_US_WEIGHT_CLASS);
+  EXPECT_EQ(os2->UsWidthClass(), OS2_US_WIDTH_CLASS);
+  EXPECT_EQ(os2->FsType(), OS2_FS_TYPE);
+  EXPECT_EQ(os2->YSubscriptXSize(), OS2_YSUBS_XSIZE);
+  EXPECT_EQ(os2->YSubscriptYSize(), OS2_YSUBS_YSIZE);
+  EXPECT_EQ(os2->YSubscriptXOffset(), OS2_YSUBS_XOFFSET);
+  EXPECT_EQ(os2->YSubscriptYOffset(), OS2_YSUBS_YOFFSET);
+  EXPECT_EQ(os2->YSuperscriptXSize(), OS2_YSUPS_XSIZE);
+  EXPECT_EQ(os2->YSuperscriptYSize(), OS2_YSUPS_YSIZE);
+  EXPECT_EQ(os2->YSuperscriptXOffset(), OS2_YSUPS_XOFFSET);
+  EXPECT_EQ(os2->YSuperscriptYOffset(), OS2_YSUPS_YOFFSET);
+  EXPECT_EQ(os2->YStrikeoutSize(), OS2_YSTRIKEOUT_SIZE);
+  EXPECT_EQ(os2->YStrikeoutPosition(), OS2_YSTRIKEOUT_POS);
+  EXPECT_EQ(os2->SFamilyClass(), OS2_SFAMILY_CLASS);
+
+  ByteVector panose;
+  os2->Panose(&panose);
+  EXPECT_EQ(panose.size(), sizeof(OS2_PANOSE));
+  for (size_t i = 0; i < panose.size(); ++i) {
+    EXPECT_EQ(panose[i], OS2_PANOSE[i]);
+  }
+
+  EXPECT_EQ(os2->UlUnicodeRange1(), OS2_UL_UNICODE_RANGE1);
+  EXPECT_EQ(os2->UlUnicodeRange2(), OS2_UL_UNICODE_RANGE2);
+  EXPECT_EQ(os2->UlUnicodeRange3(), OS2_UL_UNICODE_RANGE3);
+  EXPECT_EQ(os2->UlUnicodeRange4(), OS2_UL_UNICODE_RANGE4);
+
+  ByteVector vend_id;
+  os2->AchVendId(&vend_id);
+  EXPECT_EQ(vend_id.size(), sizeof(OS2_ACH_VEND_ID));
+  for (size_t i = 0; i < vend_id.size(); ++i) {
+    EXPECT_EQ(vend_id[i], OS2_ACH_VEND_ID[i]);
+  }
+
+  EXPECT_EQ(os2->FsSelection(), OS2_FS_SELECTION);
+  EXPECT_EQ(os2->UsFirstCharIndex(), OS2_US_FIRST_CHAR_IDX);
+  EXPECT_EQ(os2->UsLastCharIndex(), OS2_US_LAST_CHAR_IDX);
+  EXPECT_EQ(os2->STypoAscender(), OS2_STYPO_ASCENDER);
+  EXPECT_EQ(os2->STypoDescender(), OS2_STYPO_DESCENDER);
+  EXPECT_EQ(os2->STypoLineGap(), OS2_STYPO_LINE_GAP);
+  EXPECT_EQ(os2->UsWinAscent(), OS2_US_WIN_ASCENT);
+  EXPECT_EQ(os2->UsWinDescent(), OS2_US_WIN_DESCENT);
+  EXPECT_EQ(os2->UlCodePageRange1(), OS2_UL_CODE_PAGE_RANGE1);
+  EXPECT_EQ(os2->UlCodePageRange2(), OS2_UL_CODE_PAGE_RANGE2);
+
+  // TODO(arthurhsu): SxHeight() not tested
+  // TODO(arthurhsu): SCapHeight() not tested
+  // TODO(arthurhsu): UsDefaultChar() not tested
+  // TODO(arthurhsu): UsBreakChar() not tested
+  // TODO(arthurhsu): UsMaxContext() not tested
+
+  return true;
+}
+
+bool VerifyOS_2(Table* original, Table* target) {
+  EXPECT_TRUE(VerifyOS_2(original));
+  EXPECT_TRUE(VerifyOS_2(target));
+  return true;
+}
+
+}  // namespace sfntly
