00001
00002
00003
00004
00005
00006
00007
00008
00009 #include <stdlib.h>
00010 #include <string.h>
00011 #include "antiword.h"
00012
00013
00014
00015
00016
00017 static int
00018 iGet6InfoLength(int iByteNbr, const UCHAR *aucGrpprl)
00019 {
00020 int iTmp, iDel, iAdd;
00021
00022 switch (ucGetByte(iByteNbr, aucGrpprl)) {
00023 case 2: case 16: case 17: case 18: case 19: case 21: case 22:
00024 case 26: case 27: case 28: case 30: case 31: case 32: case 33:
00025 case 34: case 35: case 36: case 38: case 39: case 40: case 41:
00026 case 42: case 43: case 45: case 46: case 47: case 48: case 49:
00027 case 69: case 72: case 80: case 93: case 96: case 97: case 99:
00028 case 101: case 105: case 106: case 107: case 109: case 110: case 121:
00029 case 122: case 123: case 124: case 140: case 141: case 144: case 145:
00030 case 148: case 149: case 154: case 155: case 156: case 157: case 160:
00031 case 161: case 164: case 165: case 166: case 167: case 168: case 169:
00032 case 170: case 171: case 182: case 183: case 184: case 189: case 195:
00033 case 197: case 198:
00034 return 1 + 2;
00035 case 3: case 12: case 15: case 81: case 103: case 108: case 188:
00036 case 190: case 191:
00037 return 2 + (int)ucGetByte(iByteNbr + 1, aucGrpprl);
00038 case 20: case 70: case 74: case 192: case 194: case 196: case 200:
00039 return 1 + 4;
00040 case 23:
00041 iTmp = (int)ucGetByte(iByteNbr + 1, aucGrpprl);
00042 if (iTmp == 255) {
00043 iDel = (int)ucGetByte(iByteNbr + 2, aucGrpprl);
00044 iAdd = (int)ucGetByte(
00045 iByteNbr + 3 + iDel * 4, aucGrpprl);
00046 iTmp = 2 + iDel * 4 + iAdd * 3;
00047 }
00048 return 2 + iTmp;
00049 case 68: case 193: case 199:
00050 return 1 + 5;
00051 case 73: case 95: case 136: case 137:
00052 return 1 + 3;
00053 case 120: case 187:
00054 return 1 + 12;
00055 default:
00056 return 1 + 1;
00057 }
00058 }
00059
00060
00061
00062
00063 void
00064 vGet6DopInfo(FILE *pFile, ULONG ulStartBlock,
00065 const ULONG *aulBBD, size_t tBBDLen,
00066 const UCHAR *aucHeader)
00067 {
00068 document_block_type tDocument;
00069 UCHAR *aucBuffer;
00070 ULONG ulBeginDocpInfo, ulTmp;
00071 size_t tDocpInfoLen;
00072 USHORT usTmp;
00073
00074 ulBeginDocpInfo = ulGetLong(0x150, aucHeader);
00075 DBG_HEX(ulBeginDocpInfo);
00076 tDocpInfoLen = (size_t)ulGetLong(0x154, aucHeader);
00077 DBG_DEC(tDocpInfoLen);
00078 if (tDocpInfoLen < 28) {
00079 DBG_MSG("No Document information");
00080 return;
00081 }
00082
00083 aucBuffer = xmalloc(tDocpInfoLen);
00084 if (!bReadBuffer(pFile, ulStartBlock,
00085 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
00086 aucBuffer, ulBeginDocpInfo, tDocpInfoLen)) {
00087 aucBuffer = xfree(aucBuffer);
00088 return;
00089 }
00090
00091 usTmp = usGetWord(0x00, aucBuffer);
00092 tDocument.ucHdrFtrSpecification = (UCHAR)(usTmp >> 8);
00093 tDocument.usDefaultTabWidth = usGetWord(0x0a, aucBuffer);
00094 ulTmp = ulGetLong(0x14, aucBuffer);
00095 tDocument.tCreateDate = tConvertDTTM(ulTmp);
00096 ulTmp = ulGetLong(0x18, aucBuffer);
00097 tDocument.tRevisedDate = tConvertDTTM(ulTmp);
00098 vCreateDocumentInfoList(&tDocument);
00099
00100 aucBuffer = xfree(aucBuffer);
00101 }
00102
00103
00104
00105
00106
00107 static void
00108 vGet6SectionInfo(const UCHAR *aucGrpprl, size_t tBytes,
00109 section_block_type *pSection)
00110 {
00111 UINT uiIndex;
00112 int iFodoOff, iInfoLen, iSize, iTmp;
00113 USHORT usCcol;
00114 UCHAR ucTmp;
00115
00116 fail(aucGrpprl == NULL || pSection == NULL);
00117
00118 iFodoOff = 0;
00119 while (tBytes >= (size_t)iFodoOff + 1) {
00120 iInfoLen = 0;
00121 switch (ucGetByte(iFodoOff, aucGrpprl)) {
00122 case 133:
00123 iSize = (int)ucGetByte(iFodoOff + 1, aucGrpprl);
00124 DBG_DEC_C(iSize != 212, iSize);
00125 for (uiIndex = 0, iTmp = iFodoOff + 2;
00126 uiIndex < 9 && iTmp < iFodoOff + 2 + iSize - 15;
00127 uiIndex++, iTmp += 16) {
00128 pSection->aucNFC[uiIndex] =
00129 ucGetByte(iTmp, aucGrpprl);
00130 NO_DBG_DEC(pSection->aucNFC[uiIndex]);
00131 ucTmp = ucGetByte(iTmp + 3, aucGrpprl);
00132 NO_DBG_HEX(ucTmp);
00133 if ((ucTmp & BIT(2)) != 0) {
00134 pSection->usNeedPrevLvl |=
00135 (USHORT)BIT(uiIndex);
00136 }
00137 if ((ucTmp & BIT(3)) != 0) {
00138 pSection->usHangingIndent |=
00139 (USHORT)BIT(uiIndex);
00140 }
00141 }
00142 DBG_HEX(pSection->usNeedPrevLvl);
00143 DBG_HEX(pSection->usHangingIndent);
00144 break;
00145 case 142:
00146 ucTmp = ucGetByte(iFodoOff + 1, aucGrpprl);
00147 DBG_DEC(ucTmp);
00148 pSection->bNewPage = ucTmp != 0 && ucTmp != 1;
00149 break;
00150 case 144:
00151 usCcol = 1 + usGetWord(iFodoOff + 1, aucGrpprl);
00152 DBG_DEC(usCcol);
00153 break;
00154 case 153:
00155 pSection->ucHdrFtrSpecification =
00156 ucGetByte(iFodoOff + 1, aucGrpprl);
00157 break;
00158 default:
00159 break;
00160 }
00161 if (iInfoLen <= 0) {
00162 iInfoLen = iGet6InfoLength(iFodoOff, aucGrpprl);
00163 fail(iInfoLen <= 0);
00164 }
00165 iFodoOff += iInfoLen;
00166 }
00167 }
00168
00169
00170
00171
00172 void
00173 vGet6SepInfo(FILE *pFile, ULONG ulStartBlock,
00174 const ULONG *aulBBD, size_t tBBDLen,
00175 const UCHAR *aucHeader)
00176 {
00177 section_block_type tSection;
00178 ULONG *aulSectPage, *aulCharPos;
00179 UCHAR *aucBuffer, *aucFpage;
00180 ULONG ulBeginOfText, ulTextOffset, ulBeginSectInfo;
00181 size_t tSectInfoLen, tIndex, tOffset, tLen, tBytes;
00182 UCHAR aucTmp[2];
00183
00184 fail(pFile == NULL || aucHeader == NULL);
00185 fail(ulStartBlock > MAX_BLOCKNUMBER && ulStartBlock != END_OF_CHAIN);
00186 fail(aulBBD == NULL);
00187
00188 ulBeginOfText = ulGetLong(0x18, aucHeader);
00189 NO_DBG_HEX(ulBeginOfText);
00190 ulBeginSectInfo = ulGetLong(0x88, aucHeader);
00191 DBG_HEX(ulBeginSectInfo);
00192 tSectInfoLen = (size_t)ulGetLong(0x8c, aucHeader);
00193 DBG_DEC(tSectInfoLen);
00194 if (tSectInfoLen < 4) {
00195 DBG_DEC(tSectInfoLen);
00196 return;
00197 }
00198
00199 aucBuffer = xmalloc(tSectInfoLen);
00200 if (!bReadBuffer(pFile, ulStartBlock,
00201 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
00202 aucBuffer, ulBeginSectInfo, tSectInfoLen)) {
00203 aucBuffer = xfree(aucBuffer);
00204 return;
00205 }
00206 NO_DBG_PRINT_BLOCK(aucBuffer, tSectInfoLen);
00207
00208
00209 tLen = (tSectInfoLen - 4) / 16;
00210
00211 aulCharPos = xcalloc(tLen, sizeof(ULONG));
00212 for (tIndex = 0, tOffset = 0; tIndex < tLen; tIndex++, tOffset += 4) {
00213 ulTextOffset = ulGetLong(tOffset, aucBuffer);
00214 NO_DBG_HEX(ulTextOffset);
00215 aulCharPos[tIndex] = ulBeginOfText + ulTextOffset;
00216 NO_DBG_HEX(aulCharPos[tIndex]);
00217 }
00218
00219 aulSectPage = xcalloc(tLen, sizeof(ULONG));
00220 for (tIndex = 0, tOffset = (tLen + 1) * 4;
00221 tIndex < tLen;
00222 tIndex++, tOffset += 12) {
00223 aulSectPage[tIndex] = ulGetLong(tOffset + 2, aucBuffer);
00224 NO_DBG_HEX(aulSectPage[tIndex]);
00225 }
00226 aucBuffer = xfree(aucBuffer);
00227
00228
00229 for (tIndex = 0; tIndex < tLen; tIndex++) {
00230 if (aulSectPage[tIndex] == FC_INVALID) {
00231 vDefault2SectionInfoList(aulCharPos[tIndex]);
00232 continue;
00233 }
00234
00235 if (!bReadBuffer(pFile, ulStartBlock,
00236 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
00237 aucTmp, aulSectPage[tIndex], 2)) {
00238 continue;
00239 }
00240 tBytes = 2 + (size_t)usGetWord(0, aucTmp);
00241 NO_DBG_DEC(tBytes);
00242
00243 aucFpage = xmalloc(tBytes);
00244 if (!bReadBuffer(pFile, ulStartBlock,
00245 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
00246 aucFpage, aulSectPage[tIndex], tBytes)) {
00247 aucFpage = xfree(aucFpage);
00248 continue;
00249 }
00250 NO_DBG_PRINT_BLOCK(aucFpage, tBytes);
00251
00252 vGetDefaultSection(&tSection);
00253 vGet6SectionInfo(aucFpage + 2, tBytes - 2, &tSection);
00254 vAdd2SectionInfoList(&tSection, aulCharPos[tIndex]);
00255 aucFpage = xfree(aucFpage);
00256 }
00257 aulCharPos = xfree(aulCharPos);
00258 aulSectPage = xfree(aulSectPage);
00259 }
00260
00261
00262
00263
00264 void
00265 vGet6HdrFtrInfo(FILE *pFile, ULONG ulStartBlock,
00266 const ULONG *aulBBD, size_t tBBDLen,
00267 const UCHAR *aucHeader)
00268 {
00269 ULONG *aulCharPos;
00270 UCHAR *aucBuffer;
00271 ULONG ulHdrFtrOffset, ulBeginHdrFtrInfo;
00272 size_t tHdrFtrInfoLen, tIndex, tOffset, tLen;
00273
00274 fail(pFile == NULL || aucHeader == NULL);
00275 fail(ulStartBlock > MAX_BLOCKNUMBER && ulStartBlock != END_OF_CHAIN);
00276 fail(aulBBD == NULL);
00277
00278 ulBeginHdrFtrInfo = ulGetLong(0xb0, aucHeader);
00279 NO_DBG_HEX(ulBeginHdrFtrInfo);
00280 tHdrFtrInfoLen = (size_t)ulGetLong(0xb4, aucHeader);
00281 NO_DBG_DEC(tHdrFtrInfoLen);
00282 if (tHdrFtrInfoLen < 8) {
00283 DBG_DEC_C(tHdrFtrInfoLen != 0, tHdrFtrInfoLen);
00284 return;
00285 }
00286
00287 aucBuffer = xmalloc(tHdrFtrInfoLen);
00288 if (!bReadBuffer(pFile, ulStartBlock,
00289 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
00290 aucBuffer, ulBeginHdrFtrInfo, tHdrFtrInfoLen)) {
00291 aucBuffer = xfree(aucBuffer);
00292 return;
00293 }
00294 NO_DBG_PRINT_BLOCK(aucBuffer, tHdrFtrInfoLen);
00295
00296 tLen = tHdrFtrInfoLen / 4 - 1;
00297
00298 aulCharPos = xcalloc(tLen, sizeof(ULONG));
00299 for (tIndex = 0, tOffset = 0;
00300 tIndex < tLen;
00301 tIndex++, tOffset += 4) {
00302 ulHdrFtrOffset = ulGetLong(tOffset, aucBuffer);
00303 NO_DBG_HEX(ulHdrFtrOffset);
00304 aulCharPos[tIndex] = ulHdrFtrOffset2CharPos(ulHdrFtrOffset);
00305 NO_DBG_HEX(aulCharPos[tIndex]);
00306 }
00307 vCreat6HdrFtrInfoList(aulCharPos, tLen);
00308 aulCharPos = xfree(aulCharPos);
00309 aucBuffer = xfree(aucBuffer);
00310 }
00311
00312
00313
00314
00315 row_info_enum
00316 eGet6RowInfo(int iFodo,
00317 const UCHAR *aucGrpprl, int iBytes, row_block_type *pRow)
00318 {
00319 int iFodoOff, iInfoLen;
00320 int iIndex, iSize, iCol;
00321 int iPosCurr, iPosPrev;
00322 USHORT usTmp;
00323 BOOL bFound24_0, bFound24_1, bFound25_0, bFound25_1, bFound190;
00324
00325 fail(iFodo < 0 || aucGrpprl == NULL || pRow == NULL);
00326
00327 iFodoOff = 0;
00328 bFound24_0 = FALSE;
00329 bFound24_1 = FALSE;
00330 bFound25_0 = FALSE;
00331 bFound25_1 = FALSE;
00332 bFound190 = FALSE;
00333 while (iBytes >= iFodoOff + 1) {
00334 iInfoLen = 0;
00335 switch (ucGetByte(iFodo + iFodoOff, aucGrpprl)) {
00336 case 24:
00337 if (odd(ucGetByte(iFodo + iFodoOff + 1, aucGrpprl))) {
00338 bFound24_1 = TRUE;
00339 } else {
00340 bFound24_0 = TRUE;
00341 }
00342 break;
00343 case 25:
00344 if (odd(ucGetByte(iFodo + iFodoOff + 1, aucGrpprl))) {
00345 bFound25_1 = TRUE;
00346 } else {
00347 bFound25_0 = TRUE;
00348 }
00349 break;
00350 case 38:
00351 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00352 usTmp &= 0x0018;
00353 NO_DBG_DEC(usTmp >> 3);
00354 if (usTmp == 0) {
00355 pRow->ucBorderInfo &= ~TABLE_BORDER_TOP;
00356 } else {
00357 pRow->ucBorderInfo |= TABLE_BORDER_TOP;
00358 }
00359 break;
00360 case 39:
00361 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00362 usTmp &= 0x0018;
00363 NO_DBG_DEC(usTmp >> 3);
00364 if (usTmp == 0) {
00365 pRow->ucBorderInfo &= ~TABLE_BORDER_LEFT;
00366 } else {
00367 pRow->ucBorderInfo |= TABLE_BORDER_LEFT;
00368 }
00369 break;
00370 case 40:
00371 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00372 usTmp &= 0x0018;
00373 NO_DBG_DEC(usTmp >> 3);
00374 if (usTmp == 0) {
00375 pRow->ucBorderInfo &= ~TABLE_BORDER_BOTTOM;
00376 } else {
00377 pRow->ucBorderInfo |= TABLE_BORDER_BOTTOM;
00378 }
00379 break;
00380 case 41:
00381 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00382 usTmp &= 0x0018;
00383 NO_DBG_DEC(usTmp >> 3);
00384 if (usTmp == 0) {
00385 pRow->ucBorderInfo &= ~TABLE_BORDER_RIGHT;
00386 } else {
00387 pRow->ucBorderInfo |= TABLE_BORDER_RIGHT;
00388 }
00389 break;
00390 case 188:
00391 DBG_MSG("188: sprmTDefTable10");
00392 iSize = (int)usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00393 DBG_DEC(iSize);
00394 break;
00395 case 190:
00396 iSize = (int)usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00397 if (iSize < 6 || iBytes < iFodoOff + 7) {
00398 DBG_DEC(iSize);
00399 DBG_DEC(iFodoOff);
00400 iInfoLen = 1;
00401 break;
00402 }
00403 iCol = (int)ucGetByte(iFodo + iFodoOff + 3, aucGrpprl);
00404 if (iCol < 1 ||
00405 iBytes < iFodoOff + 3 + (iCol + 1) * 2) {
00406 DBG_DEC(iCol);
00407 DBG_DEC(iFodoOff);
00408 iInfoLen = 1;
00409 break;
00410 }
00411 if (iCol >= (int)elementsof(pRow->asColumnWidth)) {
00412 DBG_DEC(iCol);
00413 werr(1, "The number of columns is corrupt");
00414 }
00415 pRow->ucNumberOfColumns = (UCHAR)iCol;
00416 iPosPrev = (int)(short)usGetWord(
00417 iFodo + iFodoOff + 4,
00418 aucGrpprl);
00419 for (iIndex = 0; iIndex < iCol; iIndex++) {
00420 iPosCurr = (int)(short)usGetWord(
00421 iFodo + iFodoOff + 6 + iIndex * 2,
00422 aucGrpprl);
00423 pRow->asColumnWidth[iIndex] =
00424 (short)(iPosCurr - iPosPrev);
00425 iPosPrev = iPosCurr;
00426 }
00427 bFound190 = TRUE;
00428 break;
00429 default:
00430 break;
00431 }
00432 if (iInfoLen <= 0) {
00433 iInfoLen =
00434 iGet6InfoLength(iFodo + iFodoOff, aucGrpprl);
00435 fail(iInfoLen <= 0);
00436 }
00437 iFodoOff += iInfoLen;
00438 }
00439
00440 if (bFound25_1 && bFound190) {
00441 return found_end_of_row;
00442 }
00443 if (bFound25_0 && !bFound190) {
00444 return found_not_end_of_row;
00445 }
00446 if (bFound24_1) {
00447 return found_a_cell;
00448 }
00449 if (bFound24_0) {
00450 return found_not_a_cell;
00451 }
00452 return found_nothing;
00453 }
00454
00455
00456
00457
00458
00459 void
00460 vGet6StyleInfo(int iFodo,
00461 const UCHAR *aucGrpprl, int iBytes, style_block_type *pStyle)
00462 {
00463 int iFodoOff, iInfoLen;
00464 int iTmp, iDel, iAdd, iBefore;
00465 short sTmp;
00466 UCHAR ucTmp;
00467
00468 fail(iFodo < 0 || aucGrpprl == NULL || pStyle == NULL);
00469
00470 NO_DBG_DEC(pStyle->usIstd);
00471
00472 iFodoOff = 0;
00473 while (iBytes >= iFodoOff + 1) {
00474 iInfoLen = 0;
00475 switch (ucGetByte(iFodo + iFodoOff, aucGrpprl)) {
00476 case 2:
00477 sTmp = (short)ucGetByte(
00478 iFodo + iFodoOff + 1, aucGrpprl);
00479 NO_DBG_DEC(sTmp);
00480 break;
00481 case 5:
00482 pStyle->ucAlignment = ucGetByte(
00483 iFodo + iFodoOff + 1, aucGrpprl);
00484 break;
00485 case 12:
00486 iTmp = (int)ucGetByte(
00487 iFodo + iFodoOff + 1, aucGrpprl);
00488 DBG_DEC_C(iTmp < 52, iTmp);
00489 if (iTmp >= 1) {
00490 pStyle->ucNFC = ucGetByte(
00491 iFodo + iFodoOff + 2, aucGrpprl);
00492 }
00493 if (pStyle->ucNFC != LIST_BULLETS && iTmp >= 2) {
00494 iBefore = (int)ucGetByte(
00495 iFodo + iFodoOff + 3, aucGrpprl);
00496 } else {
00497 iBefore = 0;
00498 }
00499 if (iTmp >= 12) {
00500 pStyle->usStartAt = usGetWord(
00501 iFodo + iFodoOff + 12, aucGrpprl);
00502 }
00503 if (iTmp >= iBefore + 21) {
00504 pStyle->usListChar = (USHORT)ucGetByte(
00505 iFodo + iFodoOff + iBefore + 22,
00506 aucGrpprl);
00507 NO_DBG_HEX(pStyle->usListChar);
00508 }
00509 break;
00510 case 13:
00511 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00512 pStyle->ucNumLevel = ucTmp;
00513 pStyle->bNumPause =
00514 eGetNumType(ucTmp) == level_type_pause;
00515 break;
00516 case 15:
00517 case 23:
00518 iTmp = (int)ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00519 if (iTmp < 2) {
00520 iInfoLen = 1;
00521 break;
00522 }
00523 NO_DBG_DEC(iTmp);
00524 iDel = (int)ucGetByte(iFodo + iFodoOff + 2, aucGrpprl);
00525 if (iTmp < 2 + 2 * iDel) {
00526 iInfoLen = 1;
00527 break;
00528 }
00529 NO_DBG_DEC(iDel);
00530 iAdd = (int)ucGetByte(
00531 iFodo + iFodoOff + 3 + 2 * iDel, aucGrpprl);
00532 if (iTmp < 2 + 2 * iDel + 2 * iAdd) {
00533 iInfoLen = 1;
00534 break;
00535 }
00536 NO_DBG_DEC(iAdd);
00537 break;
00538 case 16:
00539 pStyle->sRightIndent = (short)usGetWord(
00540 iFodo + iFodoOff + 1, aucGrpprl);
00541 NO_DBG_DEC(pStyle->sRightIndent);
00542 break;
00543 case 17:
00544 pStyle->sLeftIndent = (short)usGetWord(
00545 iFodo + iFodoOff + 1, aucGrpprl);
00546 NO_DBG_DEC(pStyle->sLeftIndent);
00547 break;
00548 case 18:
00549 sTmp = (short)usGetWord(
00550 iFodo + iFodoOff + 1, aucGrpprl);
00551 pStyle->sLeftIndent += sTmp;
00552 if (pStyle->sLeftIndent < 0) {
00553 pStyle->sLeftIndent = 0;
00554 }
00555 NO_DBG_DEC(sTmp);
00556 NO_DBG_DEC(pStyle->sLeftIndent);
00557 break;
00558 case 19:
00559 pStyle->sLeftIndent1 = (short)usGetWord(
00560 iFodo + iFodoOff + 1, aucGrpprl);
00561 NO_DBG_DEC(pStyle->sLeftIndent1);
00562 break;
00563 case 21:
00564 pStyle->usBeforeIndent = usGetWord(
00565 iFodo + iFodoOff + 1, aucGrpprl);
00566 NO_DBG_DEC(pStyle->usBeforeIndent);
00567 break;
00568 case 22:
00569 pStyle->usAfterIndent = usGetWord(
00570 iFodo + iFodoOff + 1, aucGrpprl);
00571 NO_DBG_DEC(pStyle->usAfterIndent);
00572 break;
00573 default:
00574 break;
00575 }
00576 if (iInfoLen <= 0) {
00577 iInfoLen =
00578 iGet6InfoLength(iFodo + iFodoOff, aucGrpprl);
00579 fail(iInfoLen <= 0);
00580 }
00581 iFodoOff += iInfoLen;
00582 }
00583 }
00584
00585
00586
00587
00588 void
00589 vGet6PapInfo(FILE *pFile, ULONG ulStartBlock,
00590 const ULONG *aulBBD, size_t tBBDLen,
00591 const UCHAR *aucHeader)
00592 {
00593 row_block_type tRow;
00594 style_block_type tStyle;
00595 USHORT *ausParfPage;
00596 UCHAR *aucBuffer;
00597 ULONG ulCharPos, ulCharPosFirst, ulCharPosLast;
00598 ULONG ulBeginParfInfo;
00599 size_t tParfInfoLen, tParfPageNum, tOffset, tSize, tLenOld, tLen;
00600 size_t tIndex, tIndex2, tRun;
00601 int iFodo, iLen;
00602 row_info_enum eRowInfo;
00603 USHORT usParfFirstPage, usCount, usIstd;
00604 UCHAR aucFpage[BIG_BLOCK_SIZE];
00605
00606 fail(pFile == NULL || aucHeader == NULL);
00607 fail(ulStartBlock > MAX_BLOCKNUMBER && ulStartBlock != END_OF_CHAIN);
00608 fail(aulBBD == NULL);
00609
00610 ulBeginParfInfo = ulGetLong(0xc0, aucHeader);
00611 NO_DBG_HEX(ulBeginParfInfo);
00612 tParfInfoLen = (size_t)ulGetLong(0xc4, aucHeader);
00613 NO_DBG_DEC(tParfInfoLen);
00614 if (tParfInfoLen < 4) {
00615 DBG_DEC(tParfInfoLen);
00616 return;
00617 }
00618
00619 aucBuffer = xmalloc(tParfInfoLen);
00620 if (!bReadBuffer(pFile, ulStartBlock,
00621 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
00622 aucBuffer, ulBeginParfInfo, tParfInfoLen)) {
00623 aucBuffer = xfree(aucBuffer);
00624 return;
00625 }
00626 NO_DBG_PRINT_BLOCK(aucBuffer, tParfInfoLen);
00627
00628 tLen = (tParfInfoLen - 4) / 6;
00629 ausParfPage = xcalloc(tLen, sizeof(USHORT));
00630 for (tIndex = 0, tOffset = (tLen + 1) * 4;
00631 tIndex < tLen;
00632 tIndex++, tOffset += 2) {
00633 ausParfPage[tIndex] = usGetWord(tOffset, aucBuffer);
00634 NO_DBG_DEC(ausParfPage[tIndex]);
00635 }
00636 DBG_HEX(ulGetLong(0, aucBuffer));
00637 aucBuffer = xfree(aucBuffer);
00638 tParfPageNum = (size_t)usGetWord(0x190, aucHeader);
00639 DBG_DEC(tParfPageNum);
00640 if (tLen < tParfPageNum) {
00641
00642 tLenOld = tLen;
00643 usParfFirstPage = usGetWord(0x18c, aucHeader);
00644 DBG_DEC(usParfFirstPage);
00645 tLen += tParfPageNum - 1;
00646 tSize = tLen * sizeof(USHORT);
00647 ausParfPage = xrealloc(ausParfPage, tSize);
00648
00649 usCount = usParfFirstPage + 1;
00650 for (tIndex = tLenOld; tIndex < tLen; tIndex++) {
00651 ausParfPage[tIndex] = usCount;
00652 NO_DBG_DEC(ausParfPage[tIndex]);
00653 usCount++;
00654 }
00655 }
00656
00657 (void)memset(&tRow, 0, sizeof(tRow));
00658 ulCharPosFirst = CP_INVALID;
00659 for (tIndex = 0; tIndex < tLen; tIndex++) {
00660 if (!bReadBuffer(pFile, ulStartBlock,
00661 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
00662 aucFpage,
00663 (ULONG)ausParfPage[tIndex] * BIG_BLOCK_SIZE,
00664 BIG_BLOCK_SIZE)) {
00665 break;
00666 }
00667 tRun = (size_t)ucGetByte(0x1ff, aucFpage);
00668 NO_DBG_DEC(tRun);
00669 for (tIndex2 = 0; tIndex2 < tRun; tIndex2++) {
00670 NO_DBG_HEX(ulGetLong(tIndex2 * 4, aucFpage));
00671 iFodo = 2 * (int)ucGetByte(
00672 (tRun + 1) * 4 + tIndex2 * 7, aucFpage);
00673 if (iFodo <= 0) {
00674 continue;
00675 }
00676
00677 iLen = 2 * (int)ucGetByte(iFodo, aucFpage);
00678
00679 usIstd = (USHORT)ucGetByte(iFodo + 1, aucFpage);
00680 vFillStyleFromStylesheet(usIstd, &tStyle);
00681 vGet6StyleInfo(iFodo, aucFpage + 3, iLen - 3, &tStyle);
00682 ulCharPos = ulGetLong(tIndex2 * 4, aucFpage);
00683 NO_DBG_HEX(ulCharPos);
00684 tStyle.ulFileOffset = ulCharPos2FileOffsetX(
00685 ulCharPos, &tStyle.eListID);
00686 vAdd2StyleInfoList(&tStyle);
00687
00688 eRowInfo = eGet6RowInfo(iFodo,
00689 aucFpage + 3, iLen - 3, &tRow);
00690 switch(eRowInfo) {
00691 case found_a_cell:
00692 if (ulCharPosFirst != CP_INVALID) {
00693 break;
00694 }
00695 ulCharPosFirst = ulGetLong(
00696 tIndex2 * 4, aucFpage);
00697 NO_DBG_HEX(ulCharPosFirst);
00698 tRow.ulCharPosStart = ulCharPosFirst;
00699 tRow.ulFileOffsetStart =
00700 ulCharPos2FileOffset(ulCharPosFirst);
00701 DBG_HEX_C(tRow.ulFileOffsetStart == FC_INVALID,
00702 ulCharPosFirst);
00703 break;
00704 case found_end_of_row:
00705 ulCharPosLast = ulGetLong(
00706 tIndex2 * 4, aucFpage);
00707 NO_DBG_HEX(ulCharPosLast);
00708 tRow.ulCharPosEnd = ulCharPosLast;
00709 tRow.ulFileOffsetEnd =
00710 ulCharPos2FileOffset(ulCharPosLast);
00711 DBG_HEX_C(tRow.ulFileOffsetEnd == FC_INVALID,
00712 ulCharPosLast);
00713 vAdd2RowInfoList(&tRow);
00714 (void)memset(&tRow, 0, sizeof(tRow));
00715 ulCharPosFirst = CP_INVALID;
00716 break;
00717 case found_nothing:
00718 break;
00719 default:
00720 DBG_DEC(eRowInfo);
00721 break;
00722 }
00723 }
00724 }
00725 ausParfPage = xfree(ausParfPage);
00726 }
00727
00728
00729
00730
00731
00732
00733 void
00734 vGet6FontInfo(int iFodo, USHORT usIstd,
00735 const UCHAR *aucGrpprl, int iBytes, font_block_type *pFont)
00736 {
00737 long lTmp;
00738 int iFodoOff, iInfoLen;
00739 USHORT usTmp;
00740 UCHAR ucTmp;
00741
00742 TRACE_MSG("vGet6FontInfo");
00743
00744 fail(iFodo < 0 || aucGrpprl == NULL || pFont == NULL);
00745
00746 iFodoOff = 0;
00747 while (iBytes >= iFodoOff + 1) {
00748 switch (ucGetByte(iFodo + iFodoOff, aucGrpprl)) {
00749 case 65:
00750 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00751 if (ucTmp == 0) {
00752 pFont->usFontStyle &= ~FONT_MARKDEL;
00753 } else {
00754 pFont->usFontStyle |= FONT_MARKDEL;
00755 }
00756 break;
00757 case 80:
00758 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00759 NO_DBG_DEC(usTmp);
00760 break;
00761 case 82:
00762 pFont->usFontStyle &= FONT_HIDDEN;
00763 pFont->ucFontColor = FONT_COLOR_DEFAULT;
00764 break;
00765 case 83:
00766 DBG_MSG("83: cPlain");
00767 vFillFontFromStylesheet(usIstd, pFont);
00768 break;
00769 case 85:
00770 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00771 switch (ucTmp) {
00772 case 0:
00773 pFont->usFontStyle &= ~FONT_BOLD;
00774 break;
00775 case 1:
00776 pFont->usFontStyle |= FONT_BOLD;
00777 break;
00778 case 128:
00779 break;
00780 case 129:
00781 pFont->usFontStyle ^= FONT_BOLD;
00782 break;
00783 default:
00784 DBG_DEC(ucTmp);
00785 DBG_FIXME();
00786 break;
00787 }
00788 break;
00789 case 86:
00790 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00791 switch (ucTmp) {
00792 case 0:
00793 pFont->usFontStyle &= ~FONT_ITALIC;
00794 break;
00795 case 1:
00796 pFont->usFontStyle |= FONT_ITALIC;
00797 break;
00798 case 128:
00799 break;
00800 case 129:
00801 pFont->usFontStyle ^= FONT_ITALIC;
00802 break;
00803 default:
00804 DBG_DEC(ucTmp);
00805 DBG_FIXME();
00806 break;
00807 }
00808 break;
00809 case 87:
00810 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00811 switch (ucTmp) {
00812 case 0:
00813 pFont->usFontStyle &= ~FONT_STRIKE;
00814 break;
00815 case 1:
00816 pFont->usFontStyle |= FONT_STRIKE;
00817 break;
00818 case 128:
00819 break;
00820 case 129:
00821 pFont->usFontStyle ^= FONT_STRIKE;
00822 break;
00823 default:
00824 DBG_DEC(ucTmp);
00825 DBG_FIXME();
00826 break;
00827 }
00828 break;
00829 case 90:
00830 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00831 switch (ucTmp) {
00832 case 0:
00833 pFont->usFontStyle &= ~FONT_SMALL_CAPITALS;
00834 break;
00835 case 1:
00836 pFont->usFontStyle |= FONT_SMALL_CAPITALS;
00837 break;
00838 case 128:
00839 break;
00840 case 129:
00841 pFont->usFontStyle ^= FONT_SMALL_CAPITALS;
00842 break;
00843 default:
00844 DBG_DEC(ucTmp);
00845 DBG_FIXME();
00846 break;
00847 }
00848 break;
00849 case 91:
00850 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00851 switch (ucTmp) {
00852 case 0:
00853 pFont->usFontStyle &= ~FONT_CAPITALS;
00854 break;
00855 case 1:
00856 pFont->usFontStyle |= FONT_CAPITALS;
00857 break;
00858 case 128:
00859 break;
00860 case 129:
00861 pFont->usFontStyle ^= FONT_CAPITALS;
00862 break;
00863 default:
00864 DBG_DEC(ucTmp);
00865 DBG_FIXME();
00866 break;
00867 }
00868 break;
00869 case 92:
00870 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00871 switch (ucTmp) {
00872 case 0:
00873 pFont->usFontStyle &= ~FONT_HIDDEN;
00874 break;
00875 case 1:
00876 pFont->usFontStyle |= FONT_HIDDEN;
00877 break;
00878 case 128:
00879 break;
00880 case 129:
00881 pFont->usFontStyle ^= FONT_HIDDEN;
00882 break;
00883 default:
00884 DBG_DEC(ucTmp);
00885 DBG_FIXME();
00886 break;
00887 }
00888 break;
00889 case 93:
00890 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00891 if (usTmp <= (USHORT)UCHAR_MAX) {
00892 pFont->ucFontNumber = (UCHAR)usTmp;
00893 } else {
00894 DBG_DEC(usTmp);
00895 DBG_FIXME();
00896 pFont->ucFontNumber = 0;
00897 }
00898 break;
00899 case 94:
00900 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00901 if (ucTmp == 0 || ucTmp == 5) {
00902 pFont->usFontStyle &= ~FONT_UNDERLINE;
00903 } else {
00904 NO_DBG_MSG("Underline text");
00905 pFont->usFontStyle |= FONT_UNDERLINE;
00906 if (ucTmp == 6) {
00907 DBG_MSG("Bold text");
00908 pFont->usFontStyle |= FONT_BOLD;
00909 }
00910 }
00911 break;
00912 case 95:
00913 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00914 DBG_DEC(ucTmp);
00915 if (ucTmp != 0) {
00916 pFont->usFontSize = (USHORT)ucTmp;
00917 }
00918 ucTmp = ucGetByte(iFodo + iFodoOff + 2, aucGrpprl);
00919 DBG_DEC(ucTmp);
00920 break;
00921 case 98:
00922 pFont->ucFontColor =
00923 ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00924 break;
00925 case 99:
00926 pFont->usFontSize =
00927 usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00928 break;
00929 case 100:
00930 DBG_MSG("100: sprmCHpsInc");
00931 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00932 DBG_DEC(ucTmp);
00933 break;
00934 case 103:
00935 DBG_MSG("103: sprmCMajority");
00936 break;
00937 case 104:
00938 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
00939 ucTmp &= 0x07;
00940 if (ucTmp == 1) {
00941 pFont->usFontStyle |= FONT_SUPERSCRIPT;
00942 NO_DBG_MSG("Superscript");
00943 } else if (ucTmp == 2) {
00944 pFont->usFontStyle |= FONT_SUBSCRIPT;
00945 NO_DBG_MSG("Subscript");
00946 }
00947 break;
00948 case 106:
00949 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00950 lTmp = (long)pFont->usFontSize + (long)usTmp;
00951 if (lTmp < 8) {
00952 pFont->usFontSize = 8;
00953 } else if (lTmp > 32766) {
00954 pFont->usFontSize = 32766;
00955 } else {
00956 pFont->usFontSize = (USHORT)lTmp;
00957 }
00958 break;
00959 case 108:
00960 DBG_MSG("108: sprmCMajority50");
00961 break;
00962 case 109:
00963 DBG_MSG("109: sprmCHpsMul");
00964 usTmp = usGetWord(iFodo + iFodoOff + 1, aucGrpprl);
00965 DBG_DEC(usTmp);
00966 break;
00967 default:
00968 break;
00969 }
00970 iInfoLen = iGet6InfoLength(iFodo + iFodoOff, aucGrpprl);
00971 fail(iInfoLen <= 0);
00972 iFodoOff += iInfoLen;
00973 }
00974 }
00975
00976
00977
00978
00979
00980
00981 static BOOL
00982 bGet6PicInfo(int iFodo,
00983 const UCHAR *aucGrpprl, int iBytes, picture_block_type *pPicture)
00984 {
00985 int iFodoOff, iInfoLen;
00986 BOOL bFound;
00987 UCHAR ucTmp;
00988
00989 TRACE_MSG("vGet6PicInfo");
00990
00991 fail(iFodo < 0 || aucGrpprl == NULL || pPicture == NULL);
00992
00993 iFodoOff = 0;
00994 bFound = FALSE;
00995 while (iBytes >= iFodoOff + 1) {
00996 switch (ucGetByte(iFodo + iFodoOff, aucGrpprl)) {
00997 case 68:
00998 pPicture->ulPictureOffset = ulGetLong(
00999 iFodo + iFodoOff + 2, aucGrpprl);
01000 bFound = TRUE;
01001 break;
01002 #if 0
01003 case 71:
01004 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
01005 if (ucTmp == 0x01) {
01006
01007 return FALSE;
01008 }
01009 DBG_DEC_C(ucTmp != 0, ucTmp);
01010 break;
01011 #endif
01012 case 75:
01013 ucTmp = ucGetByte(iFodo + iFodoOff + 1, aucGrpprl);
01014 if (ucTmp == 0x01) {
01015
01016 return FALSE;
01017 }
01018 DBG_DEC_C(ucTmp != 0, ucTmp);
01019 break;
01020 default:
01021 break;
01022 }
01023 iInfoLen = iGet6InfoLength(iFodo + iFodoOff, aucGrpprl);
01024 fail(iInfoLen <= 0);
01025 iFodoOff += iInfoLen;
01026 }
01027 return bFound;
01028 }
01029
01030
01031
01032
01033 void
01034 vGet6ChrInfo(FILE *pFile, ULONG ulStartBlock,
01035 const ULONG *aulBBD, size_t tBBDLen, const UCHAR *aucHeader)
01036 {
01037 font_block_type tFont;
01038 picture_block_type tPicture;
01039 USHORT *ausCharPage;
01040 UCHAR *aucBuffer;
01041 ULONG ulFileOffset, ulCharPos, ulBeginCharInfo;
01042 size_t tCharInfoLen, tOffset, tSize, tLenOld, tLen, tCharPageNum;
01043 size_t tIndex, tIndex2, tRun;
01044 int iFodo, iLen;
01045 USHORT usCharFirstPage, usCount, usIstd;
01046 UCHAR aucFpage[BIG_BLOCK_SIZE];
01047
01048 fail(pFile == NULL || aucHeader == NULL);
01049 fail(ulStartBlock > MAX_BLOCKNUMBER && ulStartBlock != END_OF_CHAIN);
01050 fail(aulBBD == NULL);
01051
01052 ulBeginCharInfo = ulGetLong(0xb8, aucHeader);
01053 NO_DBG_HEX(lBeginCharInfo);
01054 tCharInfoLen = (size_t)ulGetLong(0xbc, aucHeader);
01055 NO_DBG_DEC(tCharInfoLen);
01056 if (tCharInfoLen < 4) {
01057 DBG_DEC(tCharInfoLen);
01058 return;
01059 }
01060
01061 aucBuffer = xmalloc(tCharInfoLen);
01062 if (!bReadBuffer(pFile, ulStartBlock,
01063 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
01064 aucBuffer, ulBeginCharInfo, tCharInfoLen)) {
01065 aucBuffer = xfree(aucBuffer);
01066 return;
01067 }
01068
01069 tLen = (tCharInfoLen - 4) / 6;
01070 ausCharPage = xcalloc(tLen, sizeof(USHORT));
01071 for (tIndex = 0, tOffset = (tLen + 1) * 4;
01072 tIndex < tLen;
01073 tIndex++, tOffset += 2) {
01074 ausCharPage[tIndex] = usGetWord(tOffset, aucBuffer);
01075 NO_DBG_DEC(ausCharPage[tIndex]);
01076 }
01077 DBG_HEX(ulGetLong(0, aucBuffer));
01078 aucBuffer = xfree(aucBuffer);
01079 tCharPageNum = (size_t)usGetWord(0x18e, aucHeader);
01080 DBG_DEC(tCharPageNum);
01081 if (tLen < tCharPageNum) {
01082
01083 tLenOld = tLen;
01084 usCharFirstPage = usGetWord(0x18a, aucHeader);
01085 DBG_DEC(usCharFirstPage);
01086 tLen += tCharPageNum - 1;
01087 tSize = tLen * sizeof(USHORT);
01088 ausCharPage = xrealloc(ausCharPage, tSize);
01089
01090 usCount = usCharFirstPage + 1;
01091 for (tIndex = tLenOld; tIndex < tLen; tIndex++) {
01092 ausCharPage[tIndex] = usCount;
01093 NO_DBG_DEC(ausCharPage[tIndex]);
01094 usCount++;
01095 }
01096 }
01097
01098 for (tIndex = 0; tIndex < tLen; tIndex++) {
01099 if (!bReadBuffer(pFile, ulStartBlock,
01100 aulBBD, tBBDLen, BIG_BLOCK_SIZE,
01101 aucFpage,
01102 (ULONG)ausCharPage[tIndex] * BIG_BLOCK_SIZE,
01103 BIG_BLOCK_SIZE)) {
01104 break;
01105 }
01106 tRun = (size_t)ucGetByte(0x1ff, aucFpage);
01107 NO_DBG_DEC(tRun);
01108 for (tIndex2 = 0; tIndex2 < tRun; tIndex2++) {
01109 ulCharPos = ulGetLong(tIndex2 * 4, aucFpage);
01110 ulFileOffset = ulCharPos2FileOffset(ulCharPos);
01111 iFodo = 2 * (int)ucGetByte(
01112 (tRun + 1) * 4 + tIndex2, aucFpage);
01113
01114 iLen = (int)ucGetByte(iFodo, aucFpage);
01115
01116 usIstd = usGetIstd(ulFileOffset);
01117 vFillFontFromStylesheet(usIstd, &tFont);
01118 if (iFodo != 0) {
01119 vGet6FontInfo(iFodo, usIstd,
01120 aucFpage + 1, iLen - 1, &tFont);
01121 }
01122 tFont.ulFileOffset = ulFileOffset;
01123 vAdd2FontInfoList(&tFont);
01124
01125 if (iFodo <= 0) {
01126 continue;
01127 }
01128
01129 (void)memset(&tPicture, 0, sizeof(tPicture));
01130 if (bGet6PicInfo(iFodo, aucFpage + 1,
01131 iLen - 1, &tPicture)) {
01132 tPicture.ulFileOffset = ulFileOffset;
01133 tPicture.ulFileOffsetPicture =
01134 ulDataPos2FileOffset(
01135 tPicture.ulPictureOffset);
01136 vAdd2PictInfoList(&tPicture);
01137 }
01138 }
01139 }
01140 ausCharPage = xfree(ausCharPage);
01141 }