jdk/src/share/native/sun/font/layout/StateTableProcessor2.cpp
changeset 16891 91e99bed64ae
parent 16890 36b30720a997
equal deleted inserted replaced
16890:36b30720a997 16891:91e99bed64ae
    43 
    43 
    44 StateTableProcessor2::StateTableProcessor2()
    44 StateTableProcessor2::StateTableProcessor2()
    45 {
    45 {
    46 }
    46 }
    47 
    47 
    48 StateTableProcessor2::StateTableProcessor2(const MorphSubtableHeader2 *morphSubtableHeader)
    48 StateTableProcessor2::StateTableProcessor2(const LEReferenceTo<MorphSubtableHeader2> &morphSubtableHeader, LEErrorCode &success)
    49   : SubtableProcessor2(morphSubtableHeader)
    49   : SubtableProcessor2(morphSubtableHeader, success), stateTableHeader(morphSubtableHeader, success),
    50 {
    50     stHeader(stateTableHeader, success, (const StateTableHeader2*)&stateTableHeader->stHeader),
    51     stateTableHeader = (const MorphStateTableHeader2 *) morphSubtableHeader;
    51     nClasses(0), classTableOffset(0), stateArrayOffset(0), entryTableOffset(0), classTable(), format(0),
    52     nClasses = SWAPL(stateTableHeader->stHeader.nClasses);
    52     stateArray()
    53     classTableOffset = SWAPL(stateTableHeader->stHeader.classTableOffset);
    53 {
    54     stateArrayOffset = SWAPL(stateTableHeader->stHeader.stateArrayOffset);
    54   if (LE_FAILURE(success)) {
    55     entryTableOffset = SWAPL(stateTableHeader->stHeader.entryTableOffset);
    55     return;
    56 
    56   }
    57     classTable = (LookupTable *) ((char *) &stateTableHeader->stHeader + classTableOffset);
    57   nClasses = SWAPL(stHeader->nClasses);
    58     format = SWAPW(classTable->format);
    58   classTableOffset = SWAPL(stHeader->classTableOffset);
    59 
    59   stateArrayOffset = SWAPL(stHeader->stateArrayOffset);
    60     stateArray = (const EntryTableIndex2 *) ((char *) &stateTableHeader->stHeader + stateArrayOffset);
    60   entryTableOffset = SWAPL(stHeader->entryTableOffset);
       
    61 
       
    62   classTable = LEReferenceTo<LookupTable>(stHeader, success, classTableOffset);
       
    63   format = SWAPW(classTable->format);
       
    64 
       
    65   stateArray = LEReferenceToArrayOf<EntryTableIndex2>(stHeader, success, stateArrayOffset, LE_UNBOUNDED_ARRAY);
    61 }
    66 }
    62 
    67 
    63 StateTableProcessor2::~StateTableProcessor2()
    68 StateTableProcessor2::~StateTableProcessor2()
    64 {
    69 {
    65 }
    70 }
    66 
    71 
    67 void StateTableProcessor2::process(LEGlyphStorage &glyphStorage)
    72 void StateTableProcessor2::process(LEGlyphStorage &glyphStorage, LEErrorCode &success)
    68 {
    73 {
       
    74     if (LE_FAILURE(success)) return;
    69     // Start at state 0
    75     // Start at state 0
    70     // XXX: How do we know when to start at state 1?
    76     // XXX: How do we know when to start at state 1?
    71     le_uint16 currentState = 0;
    77     le_uint16 currentState = 0;
    72     le_int32 glyphCount = glyphStorage.getGlyphCount();
    78     le_int32 glyphCount = glyphStorage.getGlyphCount();
    73 
    79 
    83 
    89 
    84     beginStateTable();
    90     beginStateTable();
    85     switch (format) {
    91     switch (format) {
    86         case ltfSimpleArray: {
    92         case ltfSimpleArray: {
    87 #ifdef TEST_FORMAT
    93 #ifdef TEST_FORMAT
    88             SimpleArrayLookupTable *lookupTable0 = (SimpleArrayLookupTable *) classTable;
    94           LEReferenceTo<SimpleArrayLookupTable> lookupTable0(classTable, success);
    89             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
    95           if(LE_FAILURE(success)) break;
    90                 if(LE_STATE_PATIENCE_DECR()) {
    96             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
       
    97                 if (LE_FAILURE(success)) break;
       
    98                 if (LE_STATE_PATIENCE_DECR()) {
    91                   LE_DEBUG_BAD_FONT("patience exceeded - state table not moving")
    99                   LE_DEBUG_BAD_FONT("patience exceeded - state table not moving")
    92                   break; // patience exceeded.
   100                   break; // patience exceeded.
    93                 }
   101                 }
    94                 LookupValue classCode = classCodeOOB;
   102                 LookupValue classCode = classCodeOOB;
    95                 if (currGlyph == glyphCount || currGlyph == -1) {
   103                 if (currGlyph == glyphCount || currGlyph == -1) {
   103                         classCode = classCodeDEL;
   111                         classCode = classCodeDEL;
   104                     } else {
   112                     } else {
   105                         classCode = SWAPW(lookupTable0->valueArray[gid]);
   113                         classCode = SWAPW(lookupTable0->valueArray[gid]);
   106                     }
   114                     }
   107                 }
   115                 }
   108                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray[classCode + currentState * nClasses]);
   116                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray(classCode + currentState * nClasses, success));
   109                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   117                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   110                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex); // return a zero-based index instead of a byte offset
   118                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex); // return a zero-based index instead of a byte offset
   111                 LE_STATE_PATIENCE_INCR(currGlyph);
   119                 LE_STATE_PATIENCE_INCR(currGlyph);
   112             }
   120             }
   113 #endif
   121 #endif
   114             break;
   122             break;
   115         }
   123         }
   116         case ltfSegmentSingle: {
   124         case ltfSegmentSingle: {
   117             SegmentSingleLookupTable *lookupTable2 = (SegmentSingleLookupTable *) classTable;
   125           LEReferenceTo<SegmentSingleLookupTable> lookupTable2(classTable, success);
   118             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
   126           if(LE_FAILURE(success)) break;
   119                 if(LE_STATE_PATIENCE_DECR()) {
   127             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
   120                   LE_DEBUG_BAD_FONT("patience exceeded - state table not moving")
   128                 if (LE_FAILURE(success)) break;
       
   129                 if (LE_STATE_PATIENCE_DECR()) {
       
   130                   LE_DEBUG_BAD_FONT("patience exceeded  - state table not moving")
   121                   break; // patience exceeded.
   131                   break; // patience exceeded.
   122                 }
   132                 }
   123                 LookupValue classCode = classCodeOOB;
   133                 LookupValue classCode = classCodeOOB;
   124                 if (currGlyph == glyphCount || currGlyph == -1) {
   134                 if (currGlyph == glyphCount || currGlyph == -1) {
   125                     // XXX: How do we handle EOT vs. EOL?
   135                     // XXX: How do we handle EOT vs. EOL?
   129                     TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(gid);
   139                     TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(gid);
   130 
   140 
   131                     if (glyphCode == 0xFFFF) {
   141                     if (glyphCode == 0xFFFF) {
   132                         classCode = classCodeDEL;
   142                         classCode = classCodeDEL;
   133                     } else {
   143                     } else {
   134                         const LookupSegment *segment = lookupTable2->lookupSegment(lookupTable2->segments, gid);
   144                       const LookupSegment *segment =
   135                         if (segment != NULL) {
   145                         lookupTable2->lookupSegment(lookupTable2, lookupTable2->segments, gid, success);
       
   146                         if (segment != NULL && LE_SUCCESS(success)) {
   136                             classCode = SWAPW(segment->value);
   147                             classCode = SWAPW(segment->value);
   137                         }
   148                         }
   138                     }
   149                     }
   139                 }
   150                 }
   140                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray[classCode + currentState * nClasses]);
   151                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray(classCode + currentState * nClasses,success));
   141                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   152                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   142                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex);
   153                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex, success);
   143                 LE_STATE_PATIENCE_INCR(currGlyph);
   154                 LE_STATE_PATIENCE_INCR(currGlyph);
   144             }
   155             }
   145             break;
   156             break;
   146         }
   157         }
   147         case ltfSegmentArray: {
   158         case ltfSegmentArray: {
   148           //printf("Lookup Table Format4: specific interpretation needed!\n");
   159           //printf("Lookup Table Format4: specific interpretation needed!\n");
   149             break;
   160             break;
   150         }
   161         }
   151         case ltfSingleTable: {
   162         case ltfSingleTable: {
   152             SingleTableLookupTable *lookupTable6 = (SingleTableLookupTable *) classTable;
   163             LEReferenceTo<SingleTableLookupTable> lookupTable6(classTable, success);
   153             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
   164             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
   154                 if(LE_STATE_PATIENCE_DECR()) {
   165                 if (LE_FAILURE(success)) break;
       
   166                 if (LE_STATE_PATIENCE_DECR()) {
   155                   LE_DEBUG_BAD_FONT("patience exceeded - state table not moving")
   167                   LE_DEBUG_BAD_FONT("patience exceeded - state table not moving")
   156                   break; // patience exceeded.
   168                   break; // patience exceeded.
   157                 }
   169                 }
   158                 LookupValue classCode = classCodeOOB;
   170                 LookupValue classCode = classCodeOOB;
   159                 if (currGlyph == glyphCount || currGlyph == -1) {
   171                 if (currGlyph == glyphCount || currGlyph == -1) {
   168                     TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(gid);
   180                     TTGlyphID glyphCode = (TTGlyphID) LE_GET_GLYPH(gid);
   169 
   181 
   170                     if (glyphCode == 0xFFFF) {
   182                     if (glyphCode == 0xFFFF) {
   171                         classCode = classCodeDEL;
   183                         classCode = classCodeDEL;
   172                     } else {
   184                     } else {
   173                         const LookupSingle *segment = lookupTable6->lookupSingle(lookupTable6->entries, gid);
   185                       const LookupSingle *segment = lookupTable6->lookupSingle(lookupTable6, lookupTable6->entries, gid, success);
   174                         if (segment != NULL) {
   186                         if (segment != NULL) {
   175                             classCode = SWAPW(segment->value);
   187                             classCode = SWAPW(segment->value);
   176                         }
   188                         }
   177                     }
   189                     }
   178                 }
   190                 }
   179                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray[classCode + currentState * nClasses]);
   191                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray(classCode + currentState * nClasses, success));
   180                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   192                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   181                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex);
   193                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex, success);
   182                 LE_STATE_PATIENCE_INCR(currGlyph);
   194                 LE_STATE_PATIENCE_INCR(currGlyph);
   183             }
   195             }
   184             break;
   196             break;
   185         }
   197         }
   186         case ltfTrimmedArray: {
   198         case ltfTrimmedArray: {
   187             TrimmedArrayLookupTable *lookupTable8 = (TrimmedArrayLookupTable *) classTable;
   199             LEReferenceTo<TrimmedArrayLookupTable> lookupTable8(classTable, success);
       
   200             if (LE_FAILURE(success)) break;
   188             TTGlyphID firstGlyph = SWAPW(lookupTable8->firstGlyph);
   201             TTGlyphID firstGlyph = SWAPW(lookupTable8->firstGlyph);
   189             TTGlyphID lastGlyph  = firstGlyph + SWAPW(lookupTable8->glyphCount);
   202             TTGlyphID lastGlyph  = firstGlyph + SWAPW(lookupTable8->glyphCount);
   190 
   203 
   191             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
   204             while ((dir == 1 && currGlyph <= glyphCount) || (dir == -1 && currGlyph >= -1)) {
   192                 if(LE_STATE_PATIENCE_DECR()) {
   205                 if(LE_STATE_PATIENCE_DECR()) {
   204                         classCode = classCodeDEL;
   217                         classCode = classCodeDEL;
   205                     } else if ((glyphCode >= firstGlyph) && (glyphCode < lastGlyph)) {
   218                     } else if ((glyphCode >= firstGlyph) && (glyphCode < lastGlyph)) {
   206                         classCode = SWAPW(lookupTable8->valueArray[glyphCode - firstGlyph]);
   219                         classCode = SWAPW(lookupTable8->valueArray[glyphCode - firstGlyph]);
   207                     }
   220                     }
   208                 }
   221                 }
   209                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray[classCode + currentState * nClasses]);
   222                 EntryTableIndex2 entryTableIndex = SWAPW(stateArray(classCode + currentState * nClasses, success));
   210                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   223                 LE_STATE_PATIENCE_CURR(le_int32, currGlyph);
   211                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex);
   224                 currentState = processStateEntry(glyphStorage, currGlyph, entryTableIndex, success);
   212                 LE_STATE_PATIENCE_INCR(currGlyph);
   225                 LE_STATE_PATIENCE_INCR(currGlyph);
   213             }
   226             }
   214             break;
   227             break;
   215         }
   228         }
   216         default:
   229         default: