summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFridrich Štrba <fridrich.strba@bluewin.ch>2013-05-10 09:32:20 +0200
committerFridrich Štrba <fridrich.strba@bluewin.ch>2013-05-10 09:34:44 +0200
commit20b5cdbdfd3e9f0916c8f56b2e266a20335b233a (patch)
tree66c492e59242b8c384b11f647fb36846e202ef1a
parent88535cad5dfd8bc38c1497de423c6c15494f8eb7 (diff)
Make harfbuzz Windows XP compatible
In a case we use harfbuzz on Windows once, it is using in the uniscribe backend some OpenType shaping that is available only in Vista and later. So call this functions over function pointers if available and if not, fallback to the itemizing/shaping/placing that is available in Windows XP uniscribe. Change-Id: I5b1a22d812d57194d1147effa87033cdf6af78d3
-rw-r--r--harfbuzz/UnpackedTarball_harfbuzz.mk1
-rw-r--r--harfbuzz/harfbuzz-0.9.16-winxp.patch.1137
2 files changed, 138 insertions, 0 deletions
diff --git a/harfbuzz/UnpackedTarball_harfbuzz.mk b/harfbuzz/UnpackedTarball_harfbuzz.mk
index 4b98988c9f91..f87519077ba0 100644
--- a/harfbuzz/UnpackedTarball_harfbuzz.mk
+++ b/harfbuzz/UnpackedTarball_harfbuzz.mk
@@ -13,6 +13,7 @@ $(eval $(call gb_UnpackedTarball_set_tarball,harfbuzz,$(HARFBUZZ_TARBALL)))
$(eval $(call gb_UnpackedTarball_add_patches,harfbuzz, \
harfbuzz/harfbuzz.configure.patch.1 \
+ harfbuzz/harfbuzz-0.9.16-winxp.patch.1 \
))
# vim: set noet sw=4 ts=4:
diff --git a/harfbuzz/harfbuzz-0.9.16-winxp.patch.1 b/harfbuzz/harfbuzz-0.9.16-winxp.patch.1
new file mode 100644
index 000000000000..3787136039bb
--- /dev/null
+++ b/harfbuzz/harfbuzz-0.9.16-winxp.patch.1
@@ -0,0 +1,137 @@
+--- harfbuzz-0.9.16/src/hb-uniscribe.cc 2013-04-19 03:36:12.000000000 +0200
++++ harfbuzz-0.9.16/src/hb-uniscribe.cc 2013-05-08 17:13:37.874217344 +0200
+@@ -44,6 +44,10 @@
+ #endif
+
+
++typedef HRESULT WINAPI (*SIOT)(const WCHAR*,int,int,const SCRIPT_CONTROL*,const SCRIPT_STATE*,SCRIPT_ITEM*,OPENTYPE_TAG*,int*);
++typedef HRESULT WINAPI (*SSOT)(HDC,SCRIPT_CACHE*,SCRIPT_ANALYSIS*,OPENTYPE_TAG,OPENTYPE_TAG,int*,TEXTRANGE_PROPERTIES**,int,const WCHAR*,int,int,WORD*,SCRIPT_CHARPROP*,WORD*,SCRIPT_GLYPHPROP*,int*);
++typedef HRESULT WINAPI (*SPOT)(HDC,SCRIPT_CACHE*,SCRIPT_ANALYSIS*,OPENTYPE_TAG,OPENTYPE_TAG,int*,TEXTRANGE_PROPERTIES**,int,const WCHAR*,const WORD*,const SCRIPT_CHARPROP*,int,const WORD*,const SCRIPT_GLYPHPROP*,int,int*,GOFFSET*,ABC*);
++
+ /*
+ DWORD GetFontData(
+ __in HDC hdc,
+@@ -240,6 +244,11 @@
+ hb_face_t *face = font->face;
+ hb_uniscribe_shaper_face_data_t *face_data = HB_SHAPER_DATA_GET (face);
+ hb_uniscribe_shaper_font_data_t *font_data = HB_SHAPER_DATA_GET (font);
++ SIOT siot = NULL;
++ SSOT ssot = NULL;
++ SPOT spot = NULL;
++ HMODULE hinstLib = GetModuleHandle("usp10.dll");
++
+
+ #define FAIL(...) \
+ HB_STMT_START { \
+@@ -249,6 +258,15 @@
+
+ HRESULT hr;
+
++ if (hinstLib)
++ {
++ siot = (SIOT)GetProcAddress(hinstLib, "ScriptItemizeOpenType");
++
++ ssot = (SSOT)GetProcAddress(hinstLib, "ScriptShapeOpenType");
++
++ spot = (SPOT)GetProcAddress(hinstLib, "ScriptPlaceOpenType");
++ }
++
+ retry:
+
+ unsigned int scratch_size;
+@@ -291,6 +309,7 @@
+
+ ALLOCATE_ARRAY (WORD, glyphs, glyphs_size);
+ ALLOCATE_ARRAY (SCRIPT_GLYPHPROP, glyph_props, glyphs_size);
++ ALLOCATE_ARRAY (SCRIPT_VISATTR, vis_attr, glyphs_size);
+ ALLOCATE_ARRAY (int, advances, glyphs_size);
+ ALLOCATE_ARRAY (GOFFSET, offsets, glyphs_size);
+ ALLOCATE_ARRAY (uint32_t, vis_clusters, glyphs_size);
+@@ -312,7 +331,8 @@
+ bidi_state.uBidiLevel = HB_DIRECTION_IS_FORWARD (buffer->props.direction) ? 0 : 1;
+ bidi_state.fOverrideDirection = 1;
+
+- hr = ScriptItemizeOpenType (wchars,
++ if (siot && ssot && spot) {
++ hr = siot (wchars,
+ chars_len,
+ MAX_ITEMS,
+ &bidi_control,
+@@ -320,6 +340,16 @@
+ items,
+ script_tags,
+ &item_count);
++ }
++ else {
++ hr = ScriptItemize(wchars,
++ chars_len,
++ MAX_ITEMS,
++ &bidi_control,
++ &bidi_state,
++ items,
++ &item_count);
++ }
+ if (unlikely (FAILED (hr)))
+ FAIL ("ScriptItemizeOpenType() failed: 0x%08xL", hr);
+
+@@ -344,7 +374,8 @@
+ unsigned int item_chars_len = items[i + 1].iCharPos - chars_offset;
+
+ retry_shape:
+- hr = ScriptShapeOpenType (font_data->hdc,
++ if (siot && ssot && spot) {
++ hr = ssot (font_data->hdc,
+ &font_data->script_cache,
+ &items[i].a,
+ script_tags[i],
+@@ -361,6 +392,20 @@
+ glyphs + glyphs_offset,
+ glyph_props + glyphs_offset,
+ (int *) &glyphs_len);
++ }
++ else {
++ hr = ScriptShape (font_data->hdc,
++ &font_data->script_cache,
++ wchars + chars_offset,
++ item_chars_len,
++ glyphs_size - glyphs_offset,
++ &items[i].a,
++ /* out */
++ glyphs + glyphs_offset,
++ log_clusters + chars_offset,
++ vis_attr + glyphs_offset,
++ (int *) &glyphs_len);
++ }
+
+ if (unlikely (items[i].a.fNoGlyphIndex))
+ FAIL ("ScriptShapeOpenType() set fNoGlyphIndex");
+@@ -386,7 +431,8 @@
+ for (unsigned int j = chars_offset; j < chars_offset + item_chars_len; j++)
+ log_clusters[j] += glyphs_offset;
+
+- hr = ScriptPlaceOpenType (font_data->hdc,
++ if (siot && ssot && spot) {
++ hr = spot (font_data->hdc,
+ &font_data->script_cache,
+ &items[i].a,
+ script_tags[i],
+@@ -405,6 +451,19 @@
+ advances + glyphs_offset,
+ offsets + glyphs_offset,
+ NULL);
++ }
++ else {
++ hr = ScriptPlace (font_data->hdc,
++ &font_data->script_cache,
++ glyphs + glyphs_offset,
++ glyphs_len,
++ vis_attr + glyphs_offset,
++ &items[i].a,
++ /* out */
++ advances + glyphs_offset,
++ offsets + glyphs_offset,
++ NULL);
++ }
+ if (unlikely (FAILED (hr)))
+ FAIL ("ScriptPlaceOpenType() failed: 0x%08xL", hr);
+