summaryrefslogtreecommitdiff
path: root/java/openjdk6/files/icedtea/security/20130416/8004986.patch
diff options
context:
space:
mode:
Diffstat (limited to 'java/openjdk6/files/icedtea/security/20130416/8004986.patch')
-rw-r--r--java/openjdk6/files/icedtea/security/20130416/8004986.patch374
1 files changed, 374 insertions, 0 deletions
diff --git a/java/openjdk6/files/icedtea/security/20130416/8004986.patch b/java/openjdk6/files/icedtea/security/20130416/8004986.patch
new file mode 100644
index 000000000000..2139154d9d26
--- /dev/null
+++ b/java/openjdk6/files/icedtea/security/20130416/8004986.patch
@@ -0,0 +1,374 @@
+# HG changeset patch
+# User andrew
+# Date 1365737071 -3600
+# Node ID c7ddbf756d7f35d6e782eb91b86ce2938de44fb8
+# Parent a5bbb8808ac9a6a8e20c5f267044bb0cef0bbdc1
+8004986: Better handling of glyph table
+8004987: Improve font layout
+8004994: Improve checking of glyph table
+Reviewed-by: bae, mschoene, jgodinez
+Contributed-by: steven.loomis@oracle.com
+
+diff --git a/src/share/native/sun/font/layout/ArabicLayoutEngine.cpp b/src/share/native/sun/font/layout/ArabicLayoutEngine.cpp
+--- jdk/src/share/native/sun/font/layout/ArabicLayoutEngine.cpp
++++ jdk/src/share/native/sun/font/layout/ArabicLayoutEngine.cpp
+@@ -26,7 +26,7 @@
+
+ /*
+ *
+- * (C) Copyright IBM Corp. 1998-2005 - All Rights Reserved
++ * (C) Copyright IBM Corp. 1998-2013 - All Rights Reserved
+ *
+ */
+
+@@ -155,17 +155,16 @@
+ UnicodeArabicOpenTypeLayoutEngine::UnicodeArabicOpenTypeLayoutEngine(
+ const LEFontInstance *fontInstance,
+ le_int32 scriptCode, le_int32 languageCode, le_int32 typoFlags)
+- : ArabicOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags)
++ : ArabicOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags | LE_CHAR_FILTER_FEATURE_FLAG)
+ {
+ fGSUBTable = (const GlyphSubstitutionTableHeader *) CanonShaping::glyphSubstitutionTable;
+ fGDEFTable = (const GlyphDefinitionTableHeader *) CanonShaping::glyphDefinitionTable;
+-
+- fSubstitutionFilter = new CharSubstitutionFilter(fontInstance);
++ /* OpenTypeLayoutEngine will allocate a substitution filter */
+ }
+
+ UnicodeArabicOpenTypeLayoutEngine::~UnicodeArabicOpenTypeLayoutEngine()
+ {
+- delete fSubstitutionFilter;
++ /* OpenTypeLayoutEngine will cleanup the substitution filter */
+ }
+
+ // "glyphs", "indices" -> glyphs, indices
+diff --git a/src/share/native/sun/font/layout/LETypes.h b/src/share/native/sun/font/layout/LETypes.h
+--- jdk/src/share/native/sun/font/layout/LETypes.h
++++ jdk/src/share/native/sun/font/layout/LETypes.h
+@@ -208,6 +208,35 @@
+ #define LE_CLIENT_SHIFT 24
+
+
++#ifndef LE_ASSERT_BAD_FONT
++#define LE_ASSERT_BAD_FONT 0
++#endif
++
++#if LE_ASSERT_BAD_FONT
++#include <stdio.h>
++#define LE_DEBUG_BAD_FONT(x) fprintf(stderr,"%s:%d: BAD FONT: %s\n", __FILE__, __LINE__, (x));
++#else
++#define LE_DEBUG_BAD_FONT(x)
++#endif
++
++/**
++ * Max value representable by a uintptr
++ */
++#ifndef UINTPTR_MAX
++#ifndef UINT32_MAX
++#define LE_UINTPTR_MAX 0xFFFFFFFFU
++#else
++#define LE_UINTPTR_MAX UINT32_MAX
++#endif
++#else
++#define LE_UINTPTR_MAX UINTPTR_MAX
++#endif
++
++/**
++ * Range check for overflow
++ */
++#define LE_RANGE_CHECK(type, count, ptrfn) (( (LE_UINTPTR_MAX / sizeof(type)) < count ) ? NULL : (ptrfn))
++
+ /**
+ * A convenience macro to get the Glyph ID part of an LEGlyphID.
+ *
+@@ -599,6 +628,21 @@
+ */
+ #define LE_SUCCESS(code) ((code)<=LE_NO_ERROR)
+
++enum LEFeatureENUMs {
++ LE_Kerning_FEATURE_ENUM = 0,
++ LE_Ligatures_FEATURE_ENUM = 1,
++ LE_CHAR_FILTER_FEATURE_ENUM = 31,
++};
++
++#define LE_Kerning_FEATURE_FLAG (1 << LE_Kerning_FEATURE_ENUM)
++#define LE_Ligatures_FEATURE_FLAG (1 << LE_Ligatures_FEATURE_ENUM)
++
++#define LE_CHAR_FILTER_FEATURE_ENUM 31
++
++#define LE_CHAR_FILTER_FEATURE_FLAG (1 << LE_CHAR_FILTER_FEATURE_ENUM)
++
++#define LE_DEFAULT_FEATURE_FLAG (LE_Kerning_FEATURE_FLAG | LE_Ligatures_FEATURE_FLAG) /**< default features */
++
+ /**
+ * A convenience macro to test for the failure of a LayoutEngine call.
+ *
+diff --git a/src/share/native/sun/font/layout/LayoutEngine.cpp b/src/share/native/sun/font/layout/LayoutEngine.cpp
+--- jdk/src/share/native/sun/font/layout/LayoutEngine.cpp
++++ jdk/src/share/native/sun/font/layout/LayoutEngine.cpp
+@@ -31,6 +31,7 @@
+
+ #include "LETypes.h"
+ #include "LEScripts.h"
++#include "LESwaps.h"
+ #include "LELanguages.h"
+
+ #include "LayoutEngine.h"
+@@ -387,7 +388,7 @@
+
+ adjustMarkGlyphs(&chars[offset], count, reverse, glyphStorage, &filter, success);
+
+- if (fTypoFlags & 0x1) { /* kerning enabled */
++ if (fTypoFlags & LE_Kerning_FEATURE_FLAG) { /* kerning enabled */
+ static const le_uint32 kernTableTag = LE_KERN_TABLE_TAG;
+
+ KernTable kt(fFontInstance, getFontTable(kernTableTag));
+@@ -538,7 +539,7 @@
+ {
+ // 3 -> kerning and ligatures
+ return LayoutEngine::layoutEngineFactory(fontInstance, scriptCode,
+- languageCode, 3, success);
++ languageCode, LE_DEFAULT_FEATURE_FLAG, success);
+ }
+
+ LayoutEngine *LayoutEngine::layoutEngineFactory(const LEFontInstance *fontInstance,
+@@ -621,7 +622,7 @@
+ const MorphTableHeader *morphTable =
+ (MorphTableHeader *) fontInstance->getFontTable(mortTableTag);
+
+- if (morphTable != NULL) {
++ if (morphTable != NULL && SWAPL(morphTable->version)==0x00010000) {
+ result = new GXLayoutEngine(fontInstance, scriptCode, languageCode, morphTable);
+ } else {
+ switch (scriptCode) {
+diff --git a/src/share/native/sun/font/layout/LigatureSubstProc.cpp b/src/share/native/sun/font/layout/LigatureSubstProc.cpp
+--- jdk/src/share/native/sun/font/layout/LigatureSubstProc.cpp
++++ jdk/src/share/native/sun/font/layout/LigatureSubstProc.cpp
+@@ -25,7 +25,7 @@
+
+ /*
+ *
+- * (C) Copyright IBM Corp. 1998-2004 - All Rights Reserved
++ * (C) Copyright IBM Corp. 1998-2013 - All Rights Reserved
+ *
+ */
+
+@@ -76,6 +76,10 @@
+ }
+
+ componentStack[m] = currGlyph;
++ } else if ( m == -1) {
++ // bad font- skip this glyph.
++ currGlyph++;
++ return newState;
+ }
+
+ ByteOffset actionOffset = flags & lsfActionOffsetMask;
+@@ -99,7 +103,21 @@
+ offset = action & lafComponentOffsetMask;
+ if (offset != 0) {
+ const le_int16 *offsetTable = (const le_int16 *)((char *) &ligatureSubstitutionHeader->stHeader + 2 * SignExtend(offset, lafComponentOffsetMask));
++ const le_int16 *tableEnd = (const le_int16 *)((char *) &ligatureSubstitutionHeader + 1 * SWAPW(ligatureSubstitutionHeader->length));
+
++ // Check if the font is internally consistent
++ if(tableEnd < (const le_int16*)&ligatureSubstitutionHeader // stated end wrapped around?
++ || offsetTable > tableEnd) { // offset past end of stated length?
++ currGlyph++;
++ LE_DEBUG_BAD_FONT("off end of ligature substitution header");
++ return newState; // get out! bad font
++ }
++
++ if(componentGlyph > glyphStorage.getGlyphCount()) {
++ LE_DEBUG_BAD_FONT("preposterous componentGlyph");
++ currGlyph++;
++ return newState; // get out! bad font
++ }
+ i += SWAPW(offsetTable[LE_GET_GLYPH(glyphStorage[componentGlyph])]);
+
+ if (action & (lafLast | lafStore)) {
+@@ -107,13 +125,22 @@
+ TTGlyphID ligatureGlyph = SWAPW(*ligatureOffset);
+
+ glyphStorage[componentGlyph] = LE_SET_GLYPH(glyphStorage[componentGlyph], ligatureGlyph);
++ if(mm==nComponents) {
++ LE_DEBUG_BAD_FONT("exceeded nComponents");
++ mm--; // don't overrun the stack.
++ }
+ stack[++mm] = componentGlyph;
+ i = 0;
+ } else {
+ glyphStorage[componentGlyph] = LE_SET_GLYPH(glyphStorage[componentGlyph], 0xFFFF);
+ }
+ }
+- } while (!(action & lafLast));
++#if LE_ASSERT_BAD_FONT
++ if(m<0) {
++ LE_DEBUG_BAD_FONT("m<0")
++ }
++#endif
++ } while (!(action & lafLast) && (m>=0) ); // stop if last bit is set, or if run out of items
+
+ while (mm >= 0) {
+ if (++m >= nComponents) {
+diff --git a/src/share/native/sun/font/layout/LookupProcessor.cpp b/src/share/native/sun/font/layout/LookupProcessor.cpp
+--- jdk/src/share/native/sun/font/layout/LookupProcessor.cpp
++++ jdk/src/share/native/sun/font/layout/LookupProcessor.cpp
+@@ -185,7 +185,7 @@
+ lookupSelectCount = lookupListCount;
+
+ le_int32 count, order = 0;
+- le_int32 featureReferences = 0;
++ le_uint32 featureReferences = 0;
+ const FeatureTable *featureTable = NULL;
+ LETag featureTag;
+
+@@ -196,7 +196,7 @@
+ // be the maximum number of entries in the lookupOrderArray. We can't use
+ // lookupListCount because some lookups might be referenced by more than
+ // one feature.
+- for (le_int32 feature = 0; feature < featureCount; feature += 1) {
++ for (le_uint32 feature = 0; feature < featureCount; feature += 1) {
+ le_uint16 featureIndex = SWAPW(langSysTable->featureIndexArray[feature]);
+
+ featureTable = featureListTable->getFeatureTable(featureIndex, &featureTag);
+diff --git a/src/share/native/sun/font/layout/OpenTypeLayoutEngine.cpp b/src/share/native/sun/font/layout/OpenTypeLayoutEngine.cpp
+--- jdk/src/share/native/sun/font/layout/OpenTypeLayoutEngine.cpp
++++ jdk/src/share/native/sun/font/layout/OpenTypeLayoutEngine.cpp
+@@ -100,6 +100,14 @@
+ const GlyphPositioningTableHeader *gposTable =
+ (const GlyphPositioningTableHeader *) getFontTable(gposTableTag);
+
++ applyTypoFlags();
++
++}
++
++void OpenTypeLayoutEngine::applyTypoFlags() {
++ const le_int32& typoFlags = fTypoFlags;
++ const LEFontInstance *fontInstance = fFontInstance;
++
+ // todo: switch to more flags and bitfield rather than list of feature tags?
+ switch (typoFlags) {
+ case 0: break; // default
+@@ -109,13 +117,6 @@
+ default: break;
+ }
+
+- setScriptAndLanguageTags();
+-
+- fGDEFTable = (const GlyphDefinitionTableHeader *) getFontTable(gdefTableTag);
+-
+- if (gposTable != NULL && gposTable->coversScriptAndLanguage(fScriptTag, fLangSysTag)) {
+- fGPOSTable = gposTable;
+- }
+ }
+
+ void OpenTypeLayoutEngine::reset()
+@@ -133,11 +134,16 @@
+ fFeatureOrder(FALSE), fGSUBTable(NULL), fGDEFTable(NULL),
+ fGPOSTable(NULL), fSubstitutionFilter(NULL)
+ {
++ applyTypoFlags();
+ setScriptAndLanguageTags();
+ }
+
+ OpenTypeLayoutEngine::~OpenTypeLayoutEngine()
+ {
++ if (fTypoFlags & LE_CHAR_FILTER_FEATURE_FLAG) {
++ delete fSubstitutionFilter;
++ fSubstitutionFilter = NULL;
++ }
+ reset();
+ }
+
+diff --git a/src/share/native/sun/font/layout/OpenTypeLayoutEngine.h b/src/share/native/sun/font/layout/OpenTypeLayoutEngine.h
+--- jdk/src/share/native/sun/font/layout/OpenTypeLayoutEngine.h
++++ jdk/src/share/native/sun/font/layout/OpenTypeLayoutEngine.h
+@@ -150,6 +150,11 @@
+ */
+ static const LETag languageTags[];
+
++ /**
++ * apply the typoflags. Only called by the c'tors.
++ */
++ void applyTypoFlags();
++
+ protected:
+ /**
+ * A set of "default" features. The default characterProcessing method
+diff --git a/src/share/native/sun/font/layout/StateTableProcessor.cpp b/src/share/native/sun/font/layout/StateTableProcessor.cpp
+--- jdk/src/share/native/sun/font/layout/StateTableProcessor.cpp
++++ jdk/src/share/native/sun/font/layout/StateTableProcessor.cpp
+@@ -63,6 +63,9 @@
+
+ void StateTableProcessor::process(LEGlyphStorage &glyphStorage)
+ {
++
++ LE_STATE_PATIENCE_INIT();
++
+ // Start at state 0
+ // XXX: How do we know when to start at state 1?
+ ByteOffset currentState = stateArrayOffset;
+@@ -74,6 +77,7 @@
+ beginStateTable();
+
+ while (currGlyph <= glyphCount) {
++ if(LE_STATE_PATIENCE_DECR()) break; // patience exceeded.
+ ClassCode classCode = classCodeOOB;
+ if (currGlyph == glyphCount) {
+ // XXX: How do we handle EOT vs. EOL?
+@@ -90,8 +94,9 @@
+
+ const EntryTableIndex *stateArray = (const EntryTableIndex *) ((char *) &stateTableHeader->stHeader + currentState);
+ EntryTableIndex entryTableIndex = stateArray[(le_uint8)classCode];
+-
++ LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
+ currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex);
++ LE_STATE_PATIENCE_INCR(currGlyph);
+ }
+
+ endStateTable();
+diff --git a/src/share/native/sun/font/layout/StateTables.h b/src/share/native/sun/font/layout/StateTables.h
+--- jdk/src/share/native/sun/font/layout/StateTables.h
++++ jdk/src/share/native/sun/font/layout/StateTables.h
+@@ -35,6 +35,41 @@
+ #include "LETypes.h"
+ #include "LayoutTables.h"
+
++
++
++
++/*
++ * State table loop detection.
++ * Detects if too many ( LE_STATE_PATIENCE_COUNT ) state changes occur without moving the glyph index 'g'.
++ *
++ * Usage (pseudocode):
++ *
++ * {
++ * LE_STATE_PATIENCE_INIT();
++ *
++ * int g=0; // the glyph index - expect it to be moving
++ *
++ * for(;;) {
++ * if(LE_STATE_PATIENCE_DECR()) { // decrements the patience counter
++ * // ran out of patience, get out.
++ * break;
++ * }
++ *
++ * LE_STATE_PATIENCE_CURR(int, g); // store the 'current'
++ * state = newState(state,g);
++ * g+= <something, could be zero>;
++ * LE_STATE_PATIENCE_INCR(g); // if g has moved, increment the patience counter. Otherwise leave it.
++ * }
++ *
++ */
++
++#define LE_STATE_PATIENCE_COUNT 4096 /**< give up if a state table doesn't move the glyph after this many iterations */
++#define LE_STATE_PATIENCE_INIT() le_uint32 le_patience_count = LE_STATE_PATIENCE_COUNT
++#define LE_STATE_PATIENCE_DECR() --le_patience_count==0
++#define LE_STATE_PATIENCE_CURR(type,x) type le_patience_curr=(x)
++#define LE_STATE_PATIENCE_INCR(x) if((x)!=le_patience_curr) ++le_patience_count;
++
++
+ struct StateTableHeader
+ {
+ le_int16 stateSize;