00001
00002
00003
00004
00005
00006
00007
00008
00009 #include <stdio.h>
00010 #include <stdlib.h>
00011 #include <string.h>
00012 #include <ctype.h>
00013 #if defined(__riscos)
00014 #include "DeskLib:Hourglass.h"
00015 #include "drawfile.h"
00016 #endif
00017 #include "antiword.h"
00018
00019
00020 #define INITIAL_SIZE 40
00021 #define EXTENTION_SIZE 20
00022
00023
00024
00025 #define OUTPUT_LINE() \
00026 do {\
00027 vAlign2Window(pDiag, pAnchor, lWidthMax, ucAlignment);\
00028 TRACE_MSG("after vAlign2Window");\
00029 pAnchor = pStartNewOutput(pAnchor, NULL);\
00030 pOutput = pAnchor;\
00031 } while(0)
00032
00033 #define RESET_LINE() \
00034 do {\
00035 pAnchor = pStartNewOutput(pAnchor, NULL);\
00036 pOutput = pAnchor;\
00037 } while(0)
00038
00039 #if defined(__riscos)
00040
00041 static ULONG ulDocumentLength;
00042
00043 static ULONG ulCharCounter;
00044 static int iCurrPct, iPrevPct;
00045 #endif
00046
00047 static int iWordVersion = -1;
00048
00049 static BOOL bOldMacFile = FALSE;
00050
00051 static const section_block_type *pSection = NULL;
00052 static const section_block_type *pSectionNext = NULL;
00053
00054 static options_type tOptions;
00055
00056 static const row_block_type *pRowInfo = NULL;
00057 static BOOL bStartRow = FALSE;
00058 static BOOL bEndRowNorm = FALSE;
00059 static BOOL bEndRowFast = FALSE;
00060 static BOOL bIsTableRow = FALSE;
00061
00062 static USHORT usIstdNext = ISTD_NORMAL;
00063
00064 static const style_block_type *pStyleInfo = NULL;
00065 static style_block_type tStyleNext;
00066 static BOOL bStartStyle = FALSE;
00067 static BOOL bStartStyleNext = FALSE;
00068
00069 static const font_block_type *pFontInfo = NULL;
00070 static font_block_type tFontNext;
00071 static BOOL bStartFont = FALSE;
00072 static BOOL bStartFontNext = FALSE;
00073
00074 static ULONG ulFileOffsetImage = FC_INVALID;
00075
00076
00077
00078
00079
00080 static void
00081 vUpdateCounters(void)
00082 {
00083 #if defined(__riscos)
00084 ulCharCounter++;
00085 iCurrPct = (int)((ulCharCounter * 100) / ulDocumentLength);
00086 if (iCurrPct != iPrevPct) {
00087 Hourglass_Percentage(iCurrPct);
00088 iPrevPct = iCurrPct;
00089 }
00090 #endif
00091 }
00092
00093
00094
00095
00096 BOOL
00097 bOutputContainsText(const output_type *pAnchor)
00098 {
00099 const output_type *pCurr;
00100 size_t tIndex;
00101
00102 fail(pAnchor == NULL);
00103
00104 for (pCurr = pAnchor; pCurr != NULL; pCurr = pCurr->pNext) {
00105 fail(pCurr->lStringWidth < 0);
00106 for (tIndex = 0; tIndex < pCurr->tNextFree; tIndex++) {
00107 if (isspace((int)(UCHAR)pCurr->szStorage[tIndex])) {
00108 continue;
00109 }
00110 #if defined(DEBUG)
00111 if (pCurr->szStorage[tIndex] == FILLER_CHAR) {
00112 continue;
00113 }
00114 #endif
00115 return TRUE;
00116 }
00117 }
00118 return FALSE;
00119 }
00120
00121
00122
00123
00124 static long
00125 lTotalStringWidth(const output_type *pAnchor)
00126 {
00127 const output_type *pCurr;
00128 long lTotal;
00129
00130 lTotal = 0;
00131 for (pCurr = pAnchor; pCurr != NULL; pCurr = pCurr->pNext) {
00132 DBG_DEC_C(pCurr->lStringWidth < 0, pCurr->lStringWidth);
00133 fail(pCurr->lStringWidth < 0);
00134 lTotal += pCurr->lStringWidth;
00135 }
00136 return lTotal;
00137 }
00138
00139
00140
00141
00142 static void
00143 vStoreByte(UCHAR ucChar, output_type *pOutput)
00144 {
00145 fail(pOutput == NULL);
00146
00147 if (ucChar == 0) {
00148 pOutput->szStorage[pOutput->tNextFree] = '\0';
00149 return;
00150 }
00151
00152 while (pOutput->tNextFree + 2 > pOutput->tStorageSize) {
00153 pOutput->tStorageSize += EXTENTION_SIZE;
00154 pOutput->szStorage = xrealloc(pOutput->szStorage,
00155 pOutput->tStorageSize);
00156 }
00157 pOutput->szStorage[pOutput->tNextFree] = (char)ucChar;
00158 pOutput->szStorage[pOutput->tNextFree + 1] = '\0';
00159 pOutput->tNextFree++;
00160 }
00161
00162
00163
00164
00165 static void
00166 vStoreChar(ULONG ulChar, BOOL bChangeAllowed, output_type *pOutput)
00167 {
00168 char szResult[4];
00169 size_t tIndex, tLen;
00170
00171 fail(pOutput == NULL);
00172
00173 if (tOptions.eEncoding == encoding_utf_8 && bChangeAllowed) {
00174 DBG_HEX_C(ulChar > 0xffff, ulChar);
00175 fail(ulChar > 0xffff);
00176 tLen = tUcs2Utf8(ulChar, szResult, sizeof(szResult));
00177 for (tIndex = 0; tIndex < tLen; tIndex++) {
00178 vStoreByte((UCHAR)szResult[tIndex], pOutput);
00179 }
00180 } else {
00181 DBG_HEX_C(ulChar > 0xff, ulChar);
00182 fail(ulChar > 0xff);
00183 vStoreByte((UCHAR)ulChar, pOutput);
00184 tLen = 1;
00185 }
00186 pOutput->lStringWidth += lComputeStringWidth(
00187 pOutput->szStorage + pOutput->tNextFree - tLen,
00188 tLen,
00189 pOutput->tFontRef,
00190 pOutput->usFontSize);
00191 }
00192
00193
00194
00195
00196 static void
00197 vStoreCharacter(ULONG ulChar, output_type *pOutput)
00198 {
00199 vStoreChar(ulChar, TRUE, pOutput);
00200 }
00201
00202
00203
00204
00205 static void
00206 vStoreString(const char *szString, size_t tStringLength, output_type *pOutput)
00207 {
00208 size_t tIndex;
00209
00210 fail(szString == NULL || pOutput == NULL);
00211
00212 for (tIndex = 0; tIndex < tStringLength; tIndex++) {
00213 vStoreCharacter((ULONG)(UCHAR)szString[tIndex], pOutput);
00214 }
00215 }
00216
00217
00218
00219
00220 static void
00221 vStoreNumberAsDecimal(UINT uiNumber, output_type *pOutput)
00222 {
00223 size_t tLen;
00224 char szString[3 * sizeof(UINT) + 1];
00225
00226 fail(uiNumber == 0);
00227 fail(pOutput == NULL);
00228
00229 tLen = (size_t)sprintf(szString, "%u", uiNumber);
00230 vStoreString(szString, tLen, pOutput);
00231 }
00232
00233
00234
00235
00236 static void
00237 vStoreNumberAsRoman(UINT uiNumber, output_type *pOutput)
00238 {
00239 size_t tLen;
00240 char szString[15];
00241
00242 fail(uiNumber == 0);
00243 fail(pOutput == NULL);
00244
00245 tLen = tNumber2Roman(uiNumber, FALSE, szString);
00246 vStoreString(szString, tLen, pOutput);
00247 }
00248
00249
00250
00251
00252 static void
00253 vStoreStyle(diagram_type *pDiag, output_type *pOutput,
00254 const style_block_type *pStyle)
00255 {
00256 size_t tLen;
00257 char szString[120];
00258
00259 fail(pDiag == NULL);
00260 fail(pOutput == NULL);
00261 fail(pStyle == NULL);
00262
00263 if (tOptions.eConversionType == conversion_xml) {
00264 vSetHeaders(pDiag, pStyle->usIstd);
00265 } else {
00266 tLen = tStyle2Window(szString, sizeof(szString),
00267 pStyle, pSection);
00268 vStoreString(szString, tLen, pOutput);
00269 }
00270 }
00271
00272
00273
00274
00275 static void
00276 vPutIndentation(diagram_type *pDiag, output_type *pOutput,
00277 BOOL bNoMarks, BOOL bFirstLine,
00278 UINT uiListNumber, UCHAR ucNFC, const char *szListChar,
00279 long lLeftIndentation, long lLeftIndentation1)
00280 {
00281 long lWidth;
00282 size_t tIndex, tNextFree;
00283 char szLine[30];
00284
00285 fail(pDiag == NULL);
00286 fail(pOutput == NULL);
00287 fail(szListChar == NULL);
00288 fail(lLeftIndentation < 0);
00289
00290 if (tOptions.eConversionType == conversion_xml) {
00291
00292 return;
00293 }
00294
00295 if (bNoMarks) {
00296 if (bFirstLine) {
00297 lLeftIndentation += lLeftIndentation1;
00298 }
00299 if (lLeftIndentation < 0) {
00300 lLeftIndentation = 0;
00301 }
00302 vSetLeftIndentation(pDiag, lLeftIndentation);
00303 return;
00304 }
00305 if (lLeftIndentation <= 0) {
00306 DBG_HEX_C(ucNFC != 0x00, ucNFC);
00307 vSetLeftIndentation(pDiag, 0);
00308 return;
00309 }
00310
00311 #if defined(DEBUG)
00312 if (tOptions.eEncoding == encoding_utf_8) {
00313 fail(strlen(szListChar) > 3);
00314 } else {
00315 DBG_HEX_C(iscntrl((int)szListChar[0]), szListChar[0]);
00316 fail(iscntrl((int)szListChar[0]));
00317 fail(szListChar[1] != '\0');
00318 }
00319 #endif
00320
00321 switch (ucNFC) {
00322 case LIST_ARABIC_NUM:
00323 case LIST_NUMBER_TXT:
00324 tNextFree = (size_t)sprintf(szLine, "%u", uiListNumber);
00325 break;
00326 case LIST_UPPER_ROMAN:
00327 case LIST_LOWER_ROMAN:
00328 tNextFree = tNumber2Roman(uiListNumber,
00329 ucNFC == LIST_UPPER_ROMAN, szLine);
00330 break;
00331 case LIST_UPPER_ALPHA:
00332 case LIST_LOWER_ALPHA:
00333 tNextFree = tNumber2Alpha(uiListNumber,
00334 ucNFC == LIST_UPPER_ALPHA, szLine);
00335 break;
00336 case LIST_ORDINAL_NUM:
00337 case LIST_ORDINAL_TXT:
00338 if (uiListNumber % 10 == 1 && uiListNumber != 11) {
00339 tNextFree =
00340 (size_t)sprintf(szLine, "%ust", uiListNumber);
00341 } else if (uiListNumber % 10 == 2 && uiListNumber != 12) {
00342 tNextFree =
00343 (size_t)sprintf(szLine, "%und", uiListNumber);
00344 } else if (uiListNumber % 10 == 3 && uiListNumber != 13) {
00345 tNextFree =
00346 (size_t)sprintf(szLine, "%urd", uiListNumber);
00347 } else {
00348 tNextFree =
00349 (size_t)sprintf(szLine, "%uth", uiListNumber);
00350 }
00351 break;
00352 case LIST_OUTLINE_NUM:
00353 tNextFree = (size_t)sprintf(szLine, "%02u", uiListNumber);
00354 break;
00355 case LIST_SPECIAL:
00356 case LIST_SPECIAL2:
00357 case LIST_BULLETS:
00358 tNextFree = 0;
00359 break;
00360 default:
00361 DBG_HEX(ucNFC);
00362 DBG_FIXME();
00363 tNextFree = (size_t)sprintf(szLine, "%u", uiListNumber);
00364 break;
00365 }
00366 tNextFree += (size_t)sprintf(szLine + tNextFree, "%.3s", szListChar);
00367 szLine[tNextFree++] = ' ';
00368 szLine[tNextFree] = '\0';
00369 lWidth = lComputeStringWidth(szLine, tNextFree,
00370 pOutput->tFontRef, pOutput->usFontSize);
00371 lLeftIndentation -= lWidth;
00372 if (lLeftIndentation < 0) {
00373 lLeftIndentation = 0;
00374 }
00375 vSetLeftIndentation(pDiag, lLeftIndentation);
00376 for (tIndex = 0; tIndex < tNextFree; tIndex++) {
00377 vStoreChar((ULONG)(UCHAR)szLine[tIndex], FALSE, pOutput);
00378 }
00379 }
00380
00381
00382
00383
00384
00385
00386
00387 static void
00388 vPutSeparatorLine(output_type *pOutput)
00389 {
00390 long lCharWidth;
00391 int iCounter, iChars;
00392 char szOne[2];
00393
00394 fail(pOutput == NULL);
00395
00396 szOne[0] = OUR_EM_DASH;
00397 szOne[1] = '\0';
00398 lCharWidth = lComputeStringWidth(szOne, 1,
00399 pOutput->tFontRef, pOutput->usFontSize);
00400 NO_DBG_DEC(lCharWidth);
00401 iChars = (int)((144000 + lCharWidth / 2) / lCharWidth);
00402 NO_DBG_DEC(iChars);
00403 for (iCounter = 0; iCounter < iChars; iCounter++) {
00404 vStoreCharacter((ULONG)(UCHAR)OUR_EM_DASH, pOutput);
00405 }
00406 }
00407
00408
00409
00410
00411
00412
00413 static output_type *
00414 pStartNextOutput(output_type *pCurrent)
00415 {
00416 output_type *pNew;
00417
00418 TRACE_MSG("pStartNextOutput");
00419
00420 if (pCurrent->tNextFree == 0) {
00421
00422 fail(pCurrent->szStorage[0] != '\0');
00423 fail(pCurrent->lStringWidth != 0);
00424 return pCurrent;
00425 }
00426
00427 pNew = xmalloc(sizeof(*pNew));
00428 pCurrent->pNext = pNew;
00429 pNew->tStorageSize = INITIAL_SIZE;
00430 pNew->szStorage = xmalloc(pNew->tStorageSize);
00431 pNew->szStorage[0] = '\0';
00432 pNew->tNextFree = 0;
00433 pNew->lStringWidth = 0;
00434 pNew->ucFontColor = FONT_COLOR_DEFAULT;
00435 pNew->usFontStyle = FONT_REGULAR;
00436 pNew->tFontRef = (drawfile_fontref)0;
00437 pNew->usFontSize = DEFAULT_FONT_SIZE;
00438 pNew->pPrev = pCurrent;
00439 pNew->pNext = NULL;
00440 return pNew;
00441 }
00442
00443
00444
00445
00446 static output_type *
00447 pStartNewOutput(output_type *pAnchor, output_type *pLeftOver)
00448 {
00449 output_type *pCurr, *pNext;
00450 USHORT usFontStyle, usFontSize;
00451 drawfile_fontref tFontRef;
00452 UCHAR ucFontColor;
00453
00454 TRACE_MSG("pStartNewOutput");
00455
00456 ucFontColor = FONT_COLOR_DEFAULT;
00457 usFontStyle = FONT_REGULAR;
00458 tFontRef = (drawfile_fontref)0;
00459 usFontSize = DEFAULT_FONT_SIZE;
00460
00461 pCurr = pAnchor;
00462 while (pCurr != NULL) {
00463 TRACE_MSG("Free the old output space");
00464 pNext = pCurr->pNext;
00465 pCurr->szStorage = xfree(pCurr->szStorage);
00466 if (pCurr->pNext == NULL) {
00467 ucFontColor = pCurr->ucFontColor;
00468 usFontStyle = pCurr->usFontStyle;
00469 tFontRef = pCurr->tFontRef;
00470 usFontSize = pCurr->usFontSize;
00471 }
00472 pCurr = xfree(pCurr);
00473 pCurr = pNext;
00474 }
00475 if (pLeftOver == NULL) {
00476
00477 TRACE_MSG("Create new output space");
00478 pLeftOver = xmalloc(sizeof(*pLeftOver));
00479 pLeftOver->tStorageSize = INITIAL_SIZE;
00480 NO_DBG_DEC(pLeftOver->tStorageSize);
00481 TRACE_MSG("before 2nd xmalloc");
00482 pLeftOver->szStorage = xmalloc(pLeftOver->tStorageSize);
00483 TRACE_MSG("after 2nd xmalloc");
00484 pLeftOver->szStorage[0] = '\0';
00485 pLeftOver->tNextFree = 0;
00486 pLeftOver->lStringWidth = 0;
00487 pLeftOver->ucFontColor = ucFontColor;
00488 pLeftOver->usFontStyle = usFontStyle;
00489 pLeftOver->tFontRef = tFontRef;
00490 pLeftOver->usFontSize = usFontSize;
00491 pLeftOver->pPrev = NULL;
00492 pLeftOver->pNext = NULL;
00493 }
00494 fail(!bCheckDoubleLinkedList(pLeftOver));
00495 return pLeftOver;
00496 }
00497
00498
00499
00500
00501
00502
00503 static ULONG
00504 ulGetChar(FILE *pFile, list_id_enum eListID)
00505 {
00506 const font_block_type *pCurr;
00507 ULONG ulChar, ulFileOffset, ulCharPos;
00508 row_info_enum eRowInfo;
00509 USHORT usChar, usPropMod;
00510 BOOL bSkip;
00511
00512 fail(pFile == NULL);
00513
00514 pCurr = pFontInfo;
00515 bSkip = FALSE;
00516 for (;;) {
00517 usChar = usNextChar(pFile, eListID,
00518 &ulFileOffset, &ulCharPos, &usPropMod);
00519 if (usChar == (USHORT)EOF) {
00520 return (ULONG)EOF;
00521 }
00522
00523 vUpdateCounters();
00524
00525 eRowInfo = ePropMod2RowInfo(usPropMod, iWordVersion);
00526 if (!bStartRow) {
00527 #if 0
00528 bStartRow = eRowInfo == found_a_cell ||
00529 (pRowInfo != NULL &&
00530 ulFileOffset == pRowInfo->ulFileOffsetStart &&
00531 eRowInfo != found_not_a_cell);
00532 #else
00533 bStartRow = pRowInfo != NULL &&
00534 ulFileOffset == pRowInfo->ulFileOffsetStart;
00535 #endif
00536 NO_DBG_HEX_C(bStartRow, pRowInfo->ulFileOffsetStart);
00537 }
00538 if (!bEndRowNorm) {
00539 #if 0
00540 bEndRow = eRowInfo == found_end_of_row ||
00541 (pRowInfo != NULL &&
00542 ulFileOffset == pRowInfo->ulFileOffsetEnd &&
00543 eRowInfo != found_not_end_of_row);
00544 #else
00545 bEndRowNorm = pRowInfo != NULL &&
00546 ulFileOffset == pRowInfo->ulFileOffsetEnd;
00547 #endif
00548 NO_DBG_HEX_C(bEndRowNorm, pRowInfo->ulFileOffsetEnd);
00549 }
00550 if (!bEndRowFast) {
00551 bEndRowFast = eRowInfo == found_end_of_row;
00552 NO_DBG_HEX_C(bEndRowFast, pRowInfo->ulFileOffsetEnd);
00553 }
00554
00555 if (!bStartStyle) {
00556 bStartStyle = pStyleInfo != NULL &&
00557 ulFileOffset == pStyleInfo->ulFileOffset;
00558 NO_DBG_HEX_C(bStartStyle, ulFileOffset);
00559 }
00560 if (pCurr != NULL && ulFileOffset == pCurr->ulFileOffset) {
00561 bStartFont = TRUE;
00562 NO_DBG_HEX(ulFileOffset);
00563 pFontInfo = pCurr;
00564 pCurr = pGetNextFontInfoListItem(pCurr);
00565 }
00566
00567
00568 if (usChar == START_EMBEDDED) {
00569 bSkip = TRUE;
00570 continue;
00571 }
00572 if (usChar == END_IGNORE || usChar == END_EMBEDDED) {
00573 bSkip = FALSE;
00574 continue;
00575 }
00576 if (bSkip) {
00577 continue;
00578 }
00579 ulChar = ulTranslateCharacters(usChar,
00580 ulFileOffset,
00581 iWordVersion,
00582 tOptions.eConversionType,
00583 tOptions.eEncoding,
00584 bOldMacFile);
00585 if (ulChar == IGNORE_CHARACTER) {
00586 continue;
00587 }
00588 if (ulChar == PICTURE) {
00589 ulFileOffsetImage = ulGetPictInfoListItem(ulFileOffset);
00590 } else {
00591 ulFileOffsetImage = FC_INVALID;
00592 }
00593 if (ulChar == PAR_END) {
00594
00595 vFillStyleFromStylesheet(usIstdNext, &tStyleNext);
00596 vCorrectStyleValues(&tStyleNext);
00597 bStartStyleNext = TRUE;
00598 vFillFontFromStylesheet(usIstdNext, &tFontNext);
00599 vCorrectFontValues(&tFontNext);
00600 bStartFontNext = TRUE;
00601 }
00602 if (ulChar == PAGE_BREAK) {
00603
00604 pSectionNext = pGetSectionInfo(pSection, ulCharPos);
00605 }
00606 return ulChar;
00607 }
00608 }
00609
00610
00611
00612
00613
00614
00615 static long
00616 lGetWidthMax(int iParagraphBreak)
00617 {
00618 fail(iParagraphBreak < 0);
00619
00620 if (iParagraphBreak == 0) {
00621 return LONG_MAX;
00622 }
00623 if (iParagraphBreak < MIN_SCREEN_WIDTH) {
00624 return lChar2MilliPoints(MIN_SCREEN_WIDTH);
00625 }
00626 if (iParagraphBreak > MAX_SCREEN_WIDTH) {
00627 return lChar2MilliPoints(MAX_SCREEN_WIDTH);
00628 }
00629 return lChar2MilliPoints(iParagraphBreak);
00630 }
00631
00632
00633
00634
00635
00636
00637 BOOL
00638 bWordDecryptor(FILE *pFile, long lFilesize, diagram_type *pDiag)
00639 {
00640 imagedata_type tImage;
00641 const style_block_type *pStyleTmp;
00642 const font_block_type *pFontTmp;
00643 const char *szListChar;
00644 output_type *pAnchor, *pOutput, *pLeftOver;
00645 ULONG ulChar;
00646 long lBeforeIndentation, lAfterIndentation;
00647 long lLeftIndentation, lLeftIndentation1, lRightIndentation;
00648 long lWidthCurr, lWidthMax, lDefaultTabWidth, lHalfSpaceWidth, lTmp;
00649 list_id_enum eListID;
00650 image_info_enum eRes;
00651 UINT uiFootnoteNumber, uiEndnoteNumber, uiTmp;
00652 int iListSeqNumber;
00653 BOOL bWasTableRow, bTableFontClosed, bWasEndOfParagraph;
00654 BOOL bInList, bWasInList, bNoMarks, bFirstLine;
00655 BOOL bAllCapitals, bHiddenText, bMarkDelText, bSuccess;
00656 USHORT usListNumber;
00657 USHORT usFontStyle, usFontStyleMinimal, usFontSize, usTmp;
00658 UCHAR ucFontNumber, ucFontColor;
00659 UCHAR ucNFC, ucAlignment;
00660
00661 fail(pFile == NULL || lFilesize <= 0 || pDiag == NULL);
00662
00663 TRACE_MSG("bWordDecryptor");
00664
00665 iWordVersion = iInitDocument(pFile, lFilesize);
00666 if (iWordVersion < 0) {
00667 DBG_DEC(iWordVersion);
00668 return FALSE;
00669 }
00670
00671 vGetOptions(&tOptions);
00672 bOldMacFile = bIsOldMacFile();
00673 vPrepareHdrFtrText(pFile);
00674 vPrepareFootnoteText(pFile);
00675
00676 vPrologue2(pDiag, iWordVersion);
00677
00678
00679 #if defined(__riscos)
00680 ulCharCounter = 0;
00681 iCurrPct = 0;
00682 iPrevPct = -1;
00683 ulDocumentLength = ulGetDocumentLength();
00684 #endif
00685 pSection = pGetSectionInfo(NULL, 0);
00686 pSectionNext = pSection;
00687 lDefaultTabWidth = lGetDefaultTabWidth();
00688 DBG_DEC_C(lDefaultTabWidth != 36000, lDefaultTabWidth);
00689 pRowInfo = pGetNextRowInfoListItem();
00690 DBG_HEX_C(pRowInfo != NULL, pRowInfo->ulFileOffsetStart);
00691 DBG_HEX_C(pRowInfo != NULL, pRowInfo->ulFileOffsetEnd);
00692 DBG_MSG_C(pRowInfo == NULL, "No rows at all");
00693 bStartRow = FALSE;
00694 bEndRowNorm = FALSE;
00695 bEndRowFast = FALSE;
00696 bIsTableRow = FALSE;
00697 bWasTableRow = FALSE;
00698 vResetStyles();
00699 pStyleInfo = pGetNextTextStyle(NULL);
00700 bStartStyle = FALSE;
00701 bInList = FALSE;
00702 bWasInList = FALSE;
00703 iListSeqNumber = 0;
00704 usIstdNext = ISTD_NORMAL;
00705 pAnchor = NULL;
00706 pFontInfo = pGetNextFontInfoListItem(NULL);
00707 DBG_HEX_C(pFontInfo != NULL, pFontInfo->ulFileOffset);
00708 DBG_MSG_C(pFontInfo == NULL, "No fonts at all");
00709 bStartFont = FALSE;
00710 ucFontNumber = 0;
00711 usFontStyleMinimal = FONT_REGULAR;
00712 usFontStyle = FONT_REGULAR;
00713 usFontSize = DEFAULT_FONT_SIZE;
00714 ucFontColor = FONT_COLOR_DEFAULT;
00715 pAnchor = pStartNewOutput(pAnchor, NULL);
00716 pOutput = pAnchor;
00717 pOutput->ucFontColor = ucFontColor;
00718 pOutput->usFontStyle = usFontStyle;
00719 pOutput->tFontRef = tOpenFont(ucFontNumber, usFontStyle, usFontSize);
00720 pOutput->usFontSize = usFontSize;
00721 bTableFontClosed = TRUE;
00722 lBeforeIndentation = 0;
00723 lAfterIndentation = 0;
00724 lLeftIndentation = 0;
00725 lLeftIndentation1 = 0;
00726 lRightIndentation = 0;
00727 bWasEndOfParagraph = TRUE;
00728 bNoMarks = TRUE;
00729 bFirstLine = TRUE;
00730 ucNFC = LIST_BULLETS;
00731 if (pStyleInfo != NULL) {
00732 szListChar = pStyleInfo->szListChar;
00733 pStyleTmp = pStyleInfo;
00734 } else {
00735 if (tStyleNext.szListChar[0] == '\0') {
00736 vGetBulletValue(tOptions.eConversionType,
00737 tOptions.eEncoding, tStyleNext.szListChar, 4);
00738 }
00739 szListChar = tStyleNext.szListChar;
00740 pStyleTmp = &tStyleNext;
00741 }
00742 usListNumber = 0;
00743 ucAlignment = ALIGNMENT_LEFT;
00744 bAllCapitals = FALSE;
00745 bHiddenText = FALSE;
00746 bMarkDelText = FALSE;
00747 lWidthMax = lGetWidthMax(tOptions.iParagraphBreak);
00748 NO_DBG_DEC(lWidthMax);
00749
00750 Hourglass_On();
00751
00752 uiFootnoteNumber = 0;
00753 uiEndnoteNumber = 0;
00754 eListID = text_list;
00755 for(;;) {
00756 ulChar = ulGetChar(pFile, eListID);
00757 if (ulChar == (ULONG)EOF) {
00758 if (bOutputContainsText(pAnchor)) {
00759 OUTPUT_LINE();
00760 } else {
00761 RESET_LINE();
00762 }
00763 switch (eListID) {
00764 case text_list:
00765 if (tOptions.eConversionType !=
00766 conversion_xml) {
00767 eListID = footnote_list;
00768 if (uiFootnoteNumber != 0) {
00769 vPutSeparatorLine(pAnchor);
00770 OUTPUT_LINE();
00771 uiFootnoteNumber = 0;
00772 }
00773 break;
00774 }
00775
00776 case footnote_list:
00777 eListID = endnote_list;
00778 if (uiEndnoteNumber != 0) {
00779 vPutSeparatorLine(pAnchor);
00780 OUTPUT_LINE();
00781 uiEndnoteNumber = 0;
00782 }
00783 break;
00784 case endnote_list:
00785 eListID = textbox_list;
00786 if (bExistsTextBox()) {
00787 vPutSeparatorLine(pAnchor);
00788 OUTPUT_LINE();
00789 }
00790 break;
00791 case textbox_list:
00792 eListID = hdrtextbox_list;
00793 if (bExistsHdrTextBox()) {
00794 vPutSeparatorLine(pAnchor);
00795 OUTPUT_LINE();
00796 }
00797 break;
00798 case hdrtextbox_list:
00799 default:
00800 eListID = end_of_lists;
00801 break;
00802 }
00803 if (eListID == end_of_lists) {
00804 break;
00805 }
00806 continue;
00807 }
00808
00809 if (ulChar == UNKNOWN_NOTE_CHAR) {
00810 switch (eListID) {
00811 case footnote_list:
00812 ulChar = FOOTNOTE_CHAR;
00813 break;
00814 case endnote_list:
00815 ulChar = ENDNOTE_CHAR;
00816 break;
00817 default:
00818 break;
00819 }
00820 }
00821
00822 if (bStartRow) {
00823
00824 if (bOutputContainsText(pAnchor)) {
00825 OUTPUT_LINE();
00826 } else {
00827 RESET_LINE();
00828 }
00829 fail(pAnchor != pOutput);
00830 if (bTableFontClosed) {
00831
00832 vCloseFont();
00833
00834
00835
00836
00837
00838 uiTmp = ((UINT)usFontSize * 5 + 3) / 6;
00839 if (uiTmp < MIN_TABLEFONT_SIZE) {
00840 uiTmp = MIN_TABLEFONT_SIZE;
00841 } else if (uiTmp > MAX_TABLEFONT_SIZE) {
00842 uiTmp = MAX_TABLEFONT_SIZE;
00843 }
00844 pOutput->usFontSize = (USHORT)uiTmp;
00845 pOutput->tFontRef =
00846 tOpenTableFont(pOutput->usFontSize);
00847 pOutput->usFontStyle = FONT_REGULAR;
00848 pOutput->ucFontColor = FONT_COLOR_BLACK;
00849 bTableFontClosed = FALSE;
00850 }
00851 bIsTableRow = TRUE;
00852 bStartRow = FALSE;
00853 }
00854
00855 if (bWasTableRow &&
00856 !bIsTableRow &&
00857 ulChar != PAR_END &&
00858 ulChar != HARD_RETURN &&
00859 ulChar != PAGE_BREAK &&
00860 ulChar != COLUMN_FEED) {
00861
00862
00863
00864
00865 OUTPUT_LINE();
00866 vEndOfParagraph(pDiag,
00867 pOutput->tFontRef,
00868 pOutput->usFontSize,
00869 (long)pOutput->usFontSize * 600);
00870 }
00871
00872 switch (ulChar) {
00873 case PAGE_BREAK:
00874 case COLUMN_FEED:
00875 if (bIsTableRow) {
00876
00877 break;
00878 }
00879 if (bOutputContainsText(pAnchor)) {
00880 OUTPUT_LINE();
00881 } else {
00882 RESET_LINE();
00883 }
00884 if (ulChar == PAGE_BREAK) {
00885 vEndOfPage(pDiag, lAfterIndentation,
00886 pSection != pSectionNext);
00887 } else {
00888 vEndOfParagraph(pDiag,
00889 pOutput->tFontRef,
00890 pOutput->usFontSize,
00891 lAfterIndentation);
00892 }
00893 break;
00894 default:
00895 break;
00896 }
00897
00898 if (bStartFont || (bStartFontNext && ulChar != PAR_END)) {
00899
00900 if (bStartFont) {
00901
00902 fail(pFontInfo == NULL);
00903 pFontTmp = pFontInfo;
00904 } else {
00905 pFontTmp = &tFontNext;
00906 }
00907 bAllCapitals = bIsCapitals(pFontTmp->usFontStyle);
00908 bHiddenText = bIsHidden(pFontTmp->usFontStyle);
00909 bMarkDelText = bIsMarkDel(pFontTmp->usFontStyle);
00910 usTmp = pFontTmp->usFontStyle &
00911 (FONT_BOLD|FONT_ITALIC|FONT_UNDERLINE|
00912 FONT_STRIKE|FONT_MARKDEL|
00913 FONT_SUPERSCRIPT|FONT_SUBSCRIPT);
00914 if (!bIsTableRow &&
00915 (usFontSize != pFontTmp->usFontSize ||
00916 ucFontNumber != pFontTmp->ucFontNumber ||
00917 usFontStyleMinimal != usTmp ||
00918 ucFontColor != pFontTmp->ucFontColor)) {
00919 pOutput = pStartNextOutput(pOutput);
00920 vCloseFont();
00921 pOutput->ucFontColor = pFontTmp->ucFontColor;
00922 pOutput->usFontStyle = pFontTmp->usFontStyle;
00923 pOutput->usFontSize = pFontTmp->usFontSize;
00924 pOutput->tFontRef = tOpenFont(
00925 pFontTmp->ucFontNumber,
00926 pFontTmp->usFontStyle,
00927 pFontTmp->usFontSize);
00928 fail(!bCheckDoubleLinkedList(pAnchor));
00929 }
00930 ucFontNumber = pFontTmp->ucFontNumber;
00931 usFontSize = pFontTmp->usFontSize;
00932 ucFontColor = pFontTmp->ucFontColor;
00933 usFontStyle = pFontTmp->usFontStyle;
00934 usFontStyleMinimal = usTmp;
00935 if (bStartFont) {
00936
00937 pFontInfo = pGetNextFontInfoListItem(pFontInfo);
00938 NO_DBG_HEX_C(pFontInfo != NULL,
00939 pFontInfo->ulFileOffset);
00940 DBG_MSG_C(pFontInfo == NULL, "No more fonts");
00941 }
00942 bStartFont = FALSE;
00943 bStartFontNext = FALSE;
00944 }
00945
00946 if (bStartStyle || (bStartStyleNext && ulChar != PAR_END)) {
00947 bFirstLine = TRUE;
00948
00949 if (bStartStyle) {
00950
00951 fail(pStyleInfo == NULL);
00952 pStyleTmp = pStyleInfo;
00953 } else {
00954 pStyleTmp = &tStyleNext;
00955 }
00956 if (!bIsTableRow) {
00957 vStoreStyle(pDiag, pOutput, pStyleTmp);
00958 }
00959 usIstdNext = pStyleTmp->usIstdNext;
00960 lBeforeIndentation =
00961 lTwips2MilliPoints(pStyleTmp->usBeforeIndent);
00962 lAfterIndentation =
00963 lTwips2MilliPoints(pStyleTmp->usAfterIndent);
00964 lLeftIndentation =
00965 lTwips2MilliPoints(pStyleTmp->sLeftIndent);
00966 lLeftIndentation1 =
00967 lTwips2MilliPoints(pStyleTmp->sLeftIndent1);
00968 lRightIndentation =
00969 lTwips2MilliPoints(pStyleTmp->sRightIndent);
00970 bInList = bStyleImpliesList(pStyleTmp, iWordVersion);
00971 bNoMarks = !bInList || pStyleTmp->bNumPause;
00972 ucNFC = pStyleTmp->ucNFC;
00973 szListChar = pStyleTmp->szListChar;
00974 ucAlignment = pStyleTmp->ucAlignment;
00975 if (bInList && !bWasInList) {
00976
00977 iListSeqNumber++;
00978 vStartOfList(pDiag, ucNFC,
00979 bWasTableRow && !bIsTableRow);
00980 }
00981 if (!bInList && bWasInList) {
00982
00983 vEndOfList(pDiag);
00984 }
00985 bWasInList = bInList;
00986 if (bStartStyle) {
00987 pStyleInfo = pGetNextTextStyle(pStyleInfo);
00988 NO_DBG_HEX_C(pStyleInfo != NULL,
00989 pStyleInfo->ulFileOffset);
00990 DBG_MSG_C(pStyleInfo == NULL,
00991 "No more styles");
00992 }
00993 bStartStyle = FALSE;
00994 bStartStyleNext = FALSE;
00995 }
00996
00997 if (bWasEndOfParagraph) {
00998 vStartOfParagraph1(pDiag, lBeforeIndentation);
00999 }
01000
01001 if (!bIsTableRow &&
01002 lTotalStringWidth(pAnchor) == 0) {
01003 if (!bNoMarks) {
01004 usListNumber = usGetListValue(iListSeqNumber,
01005 iWordVersion,
01006 pStyleTmp);
01007 }
01008 if (bInList && bFirstLine) {
01009 vStartOfListItem(pDiag, bNoMarks);
01010 }
01011 vPutIndentation(pDiag, pAnchor, bNoMarks, bFirstLine,
01012 usListNumber, ucNFC, szListChar,
01013 lLeftIndentation, lLeftIndentation1);
01014 bFirstLine = FALSE;
01015
01016 bNoMarks = TRUE;
01017 }
01018
01019 if (bWasEndOfParagraph) {
01020 vStartOfParagraph2(pDiag);
01021 bWasEndOfParagraph = FALSE;
01022 }
01023
01024 switch (ulChar) {
01025 case PICTURE:
01026 (void)memset(&tImage, 0, sizeof(tImage));
01027 eRes = eExamineImage(pFile, ulFileOffsetImage, &tImage);
01028 switch (eRes) {
01029 case image_no_information:
01030 bSuccess = FALSE;
01031 break;
01032 case image_minimal_information:
01033 case image_full_information:
01034 #if 0
01035 if (bOutputContainsText(pAnchor)) {
01036 OUTPUT_LINE();
01037 } else {
01038 RESET_LINE();
01039 }
01040 #endif
01041 bSuccess = bTranslateImage(pDiag, pFile,
01042 eRes == image_minimal_information,
01043 ulFileOffsetImage, &tImage);
01044 break;
01045 default:
01046 DBG_DEC(eRes);
01047 bSuccess = FALSE;
01048 break;
01049 }
01050 if (!bSuccess) {
01051 vStoreString("[pic]", 5, pOutput);
01052 }
01053 break;
01054 case FOOTNOTE_CHAR:
01055 uiFootnoteNumber++;
01056 if (tOptions.eConversionType == conversion_xml) {
01057 vStoreCharacter((ULONG)FOOTNOTE_OR_ENDNOTE,
01058 pOutput);
01059 break;
01060 }
01061 vStoreCharacter((ULONG)'[', pOutput);
01062 vStoreNumberAsDecimal(uiFootnoteNumber, pOutput);
01063 vStoreCharacter((ULONG)']', pOutput);
01064 break;
01065 case ENDNOTE_CHAR:
01066 uiEndnoteNumber++;
01067 vStoreCharacter((ULONG)'[', pOutput);
01068 vStoreNumberAsRoman(uiEndnoteNumber, pOutput);
01069 vStoreCharacter((ULONG)']', pOutput);
01070 break;
01071 case UNKNOWN_NOTE_CHAR:
01072 vStoreString("[?]", 3, pOutput);
01073 break;
01074 case PAR_END:
01075 if (bIsTableRow) {
01076 vStoreCharacter((ULONG)'\n', pOutput);
01077 break;
01078 }
01079 if (bOutputContainsText(pAnchor)) {
01080 OUTPUT_LINE();
01081 } else {
01082 vMove2NextLine(pDiag,
01083 pOutput->tFontRef, pOutput->usFontSize);
01084 RESET_LINE();
01085 }
01086 vEndOfParagraph(pDiag,
01087 pOutput->tFontRef,
01088 pOutput->usFontSize,
01089 lAfterIndentation);
01090 bWasEndOfParagraph = TRUE;
01091 break;
01092 case HARD_RETURN:
01093 if (bIsTableRow) {
01094 vStoreCharacter((ULONG)'\n', pOutput);
01095 break;
01096 }
01097 if (bOutputContainsText(pAnchor)) {
01098 OUTPUT_LINE();
01099 } else {
01100 vMove2NextLine(pDiag,
01101 pOutput->tFontRef, pOutput->usFontSize);
01102 RESET_LINE();
01103 }
01104 break;
01105 case PAGE_BREAK:
01106 case COLUMN_FEED:
01107 pSection = pSectionNext;
01108 break;
01109 case TABLE_SEPARATOR:
01110 if (bIsTableRow) {
01111 vStoreCharacter(ulChar, pOutput);
01112 break;
01113 }
01114 vStoreCharacter((ULONG)' ', pOutput);
01115 vStoreCharacter((ULONG)TABLE_SEPARATOR_CHAR, pOutput);
01116 break;
01117 case TAB:
01118 if (bIsTableRow ||
01119 tOptions.eConversionType == conversion_xml) {
01120 vStoreCharacter((ULONG)' ', pOutput);
01121 break;
01122 }
01123 if (tOptions.iParagraphBreak == 0 &&
01124 (tOptions.eConversionType == conversion_text ||
01125 tOptions.eConversionType == conversion_fmt_text)) {
01126
01127 vStoreCharacter(TAB, pOutput);
01128 break;
01129 }
01130 lHalfSpaceWidth = (lComputeSpaceWidth(
01131 pOutput->tFontRef,
01132 pOutput->usFontSize) + 1) / 2;
01133 lTmp = lTotalStringWidth(pAnchor);
01134 lTmp += lDrawUnits2MilliPoints(pDiag->lXleft);
01135 lTmp /= lDefaultTabWidth;
01136 do {
01137 vStoreCharacter((ULONG)FILLER_CHAR, pOutput);
01138 lWidthCurr = lTotalStringWidth(pAnchor);
01139 lWidthCurr +=
01140 lDrawUnits2MilliPoints(pDiag->lXleft);
01141 } while (lTmp == lWidthCurr / lDefaultTabWidth &&
01142 lWidthCurr < lWidthMax + lRightIndentation);
01143 break;
01144 default:
01145 if (bHiddenText && tOptions.bHideHiddenText) {
01146 continue;
01147 }
01148 if (bMarkDelText && tOptions.bRemoveRemovedText) {
01149 continue;
01150 }
01151 if (ulChar == UNICODE_ELLIPSIS &&
01152 tOptions.eEncoding != encoding_utf_8) {
01153 vStoreString("...", 3, pOutput);
01154 } else {
01155 if (bAllCapitals) {
01156 ulChar = ulToUpper(ulChar);
01157 }
01158 vStoreCharacter(ulChar, pOutput);
01159 }
01160 break;
01161 }
01162
01163 if (bWasTableRow && !bIsTableRow) {
01164
01165 vEndOfTable(pDiag);
01166
01167 NO_DBG_MSG("End of table font");
01168 vCloseFont();
01169 bTableFontClosed = TRUE;
01170 pOutput->ucFontColor = ucFontColor;
01171 pOutput->usFontStyle = usFontStyle;
01172 pOutput->usFontSize = usFontSize;
01173 pOutput->tFontRef = tOpenFont(
01174 ucFontNumber, usFontStyle, usFontSize);
01175 }
01176 bWasTableRow = bIsTableRow;
01177
01178 if (bIsTableRow) {
01179 fail(pAnchor != pOutput);
01180 if (!bEndRowNorm && !bEndRowFast) {
01181 continue;
01182 }
01183
01184 if (bEndRowNorm) {
01185 fail(pRowInfo == NULL);
01186 vTableRow2Window(pDiag, pAnchor, pRowInfo,
01187 tOptions.eConversionType,
01188 tOptions.iParagraphBreak);
01189 } else {
01190 fail(!bEndRowFast);
01191 }
01192
01193 pAnchor = pStartNewOutput(pAnchor, NULL);
01194 pOutput = pAnchor;
01195 if (bEndRowNorm) {
01196 pRowInfo = pGetNextRowInfoListItem();
01197 }
01198 bIsTableRow = FALSE;
01199 bEndRowNorm = FALSE;
01200 bEndRowFast = FALSE;
01201 NO_DBG_HEX_C(pRowInfo != NULL,
01202 pRowInfo->ulFileOffsetStart);
01203 NO_DBG_HEX_C(pRowInfo != NULL,
01204 pRowInfo->ulFileOffsetEnd);
01205 continue;
01206 }
01207 lWidthCurr = lTotalStringWidth(pAnchor);
01208 lWidthCurr += lDrawUnits2MilliPoints(pDiag->lXleft);
01209 if (lWidthCurr < lWidthMax + lRightIndentation) {
01210 continue;
01211 }
01212 pLeftOver = pSplitList(pAnchor);
01213 vJustify2Window(pDiag, pAnchor,
01214 lWidthMax, lRightIndentation, ucAlignment);
01215 pAnchor = pStartNewOutput(pAnchor, pLeftOver);
01216 for (pOutput = pAnchor;
01217 pOutput->pNext != NULL;
01218 pOutput = pOutput->pNext)
01219 ;
01220 fail(pOutput == NULL);
01221 if (lTotalStringWidth(pAnchor) > 0) {
01222 vSetLeftIndentation(pDiag, lLeftIndentation);
01223 }
01224 }
01225
01226 pAnchor = pStartNewOutput(pAnchor, NULL);
01227 pAnchor->szStorage = xfree(pAnchor->szStorage);
01228 pAnchor = xfree(pAnchor);
01229 vCloseFont();
01230 vFreeDocument();
01231 Hourglass_Off();
01232 return TRUE;
01233 }
01234
01235
01236
01237
01238 static long
01239 lLastStringWidth(const output_type *pAnchor)
01240 {
01241 const output_type *pCurr, *pStart;
01242
01243 pStart = NULL;
01244 for (pCurr = pAnchor; pCurr != NULL; pCurr = pCurr->pNext) {
01245 if (pCurr->tNextFree == 1 &&
01246 (pCurr->szStorage[0] == PAR_END ||
01247 pCurr->szStorage[0] == HARD_RETURN)) {
01248
01249 pStart = pCurr->pNext;
01250 }
01251 }
01252 if (pStart == NULL) {
01253
01254 pStart = pAnchor;
01255 }
01256 return lTotalStringWidth(pStart);
01257 }
01258
01259
01260
01261
01262 output_type *
01263 pHdrFtrDecryptor(FILE *pFile, ULONG ulCharPosStart, ULONG ulCharPosNext)
01264 {
01265 output_type *pAnchor, *pOutput, *pLeftOver;
01266 ULONG ulChar, ulFileOffset, ulCharPos;
01267 long lWidthCurr, lWidthMax;
01268 long lRightIndentation;
01269 USHORT usChar;
01270 UCHAR ucAlignment;
01271 BOOL bSkip;
01272
01273 fail(iWordVersion < 0);
01274 fail(tOptions.eConversionType == conversion_unknown);
01275 fail(tOptions.eEncoding == 0);
01276
01277 if (ulCharPosStart == ulCharPosNext) {
01278
01279 return NULL;
01280 }
01281
01282 lRightIndentation = 0;
01283 ucAlignment = ALIGNMENT_LEFT;
01284 bSkip = FALSE;
01285 lWidthMax = lGetWidthMax(tOptions.iParagraphBreak);
01286 pAnchor = pStartNewOutput(NULL, NULL);
01287 pOutput = pAnchor;
01288 pOutput->tFontRef = tOpenFont(0, FONT_REGULAR, DEFAULT_FONT_SIZE);
01289 usChar = usToHdrFtrPosition(pFile, ulCharPosStart);
01290 ulCharPos = ulCharPosStart;
01291 ulFileOffset = ulCharPos2FileOffset(ulCharPos);
01292 while (usChar != (USHORT)EOF && ulCharPos != ulCharPosNext) {
01293
01294 if (usChar == START_EMBEDDED) {
01295 bSkip = TRUE;
01296 } else if (usChar == END_IGNORE || usChar == END_EMBEDDED) {
01297 bSkip = FALSE;
01298 }
01299
01300 if (bSkip || usChar == END_IGNORE || usChar == END_EMBEDDED) {
01301 ulChar = IGNORE_CHARACTER;
01302 } else {
01303 ulChar = ulTranslateCharacters(usChar,
01304 ulFileOffset,
01305 iWordVersion,
01306 tOptions.eConversionType,
01307 tOptions.eEncoding,
01308 bOldMacFile);
01309 }
01310
01311 if (ulChar != IGNORE_CHARACTER) {
01312 switch (ulChar) {
01313 case PICTURE:
01314 vStoreString("[pic]", 5, pOutput);
01315 break;
01316 case PAR_END:
01317 case HARD_RETURN:
01318 case PAGE_BREAK:
01319 case COLUMN_FEED:
01320
01321 pOutput = pStartNextOutput(pOutput);
01322 vCloseFont();
01323 pOutput->tFontRef = tOpenFont(0,
01324 FONT_REGULAR, DEFAULT_FONT_SIZE);
01325
01326 if (ulChar == HARD_RETURN) {
01327 vStoreCharacter(HARD_RETURN, pOutput);
01328 } else {
01329 vStoreCharacter(PAR_END, pOutput);
01330 }
01331
01332 pOutput = pStartNextOutput(pOutput);
01333 vCloseFont();
01334 pOutput->tFontRef = tOpenFont(0,
01335 FONT_REGULAR, DEFAULT_FONT_SIZE);
01336 fail(!bCheckDoubleLinkedList(pAnchor));
01337 break;
01338 case TABLE_SEPARATOR:
01339 vStoreCharacter((ULONG)' ', pOutput);
01340 vStoreCharacter((ULONG)TABLE_SEPARATOR_CHAR,
01341 pOutput);
01342 break;
01343 case TAB:
01344 vStoreCharacter((ULONG)FILLER_CHAR, pOutput);
01345 break;
01346 default:
01347 vStoreCharacter(ulChar, pOutput);
01348 break;
01349 }
01350 }
01351 lWidthCurr = lLastStringWidth(pAnchor);
01352 if (lWidthCurr >= lWidthMax + lRightIndentation) {
01353 pLeftOver = pSplitList(pAnchor);
01354 for (pOutput = pAnchor;
01355 pOutput->pNext != NULL;
01356 pOutput = pOutput->pNext)
01357 ;
01358 fail(pOutput == NULL);
01359
01360 pOutput = pStartNextOutput(pOutput);
01361
01362 vStoreCharacter(HARD_RETURN, pOutput);
01363
01364 pOutput->pNext = pLeftOver;
01365 if (pLeftOver != NULL) {
01366 pLeftOver->pPrev = pOutput;
01367 }
01368 fail(!bCheckDoubleLinkedList(pAnchor));
01369 for (pOutput = pAnchor;
01370 pOutput->pNext != NULL;
01371 pOutput = pOutput->pNext)
01372 ;
01373 fail(pOutput == NULL);
01374 }
01375 usChar = usNextChar(pFile, hdrftr_list,
01376 &ulFileOffset, &ulCharPos, NULL);
01377 }
01378 vCloseFont();
01379 if (bOutputContainsText(pAnchor)) {
01380 return pAnchor;
01381 }
01382 pAnchor = pStartNewOutput(pAnchor, NULL);
01383 pAnchor->szStorage = xfree(pAnchor->szStorage);
01384 pAnchor = xfree(pAnchor);
01385 return NULL;
01386 }
01387
01388
01389
01390
01391 char *
01392 szFootnoteDecryptor(FILE *pFile, ULONG ulCharPosStart, ULONG ulCharPosNext)
01393 {
01394 char *szText;
01395 ULONG ulChar, ulFileOffset, ulCharPos;
01396 USHORT usChar;
01397 size_t tLen, tIndex, tNextFree, tStorageSize;
01398 char szResult[6];
01399 BOOL bSkip;
01400
01401 fail(iWordVersion < 0);
01402 fail(tOptions.eConversionType == conversion_unknown);
01403 fail(tOptions.eEncoding == 0);
01404
01405 if (ulCharPosStart == ulCharPosNext) {
01406
01407 return NULL;
01408 }
01409
01410 if (tOptions.eConversionType != conversion_xml) {
01411
01412 return NULL;
01413 }
01414
01415 bSkip = FALSE;
01416
01417
01418 tStorageSize = INITIAL_SIZE;
01419 szText = xmalloc(tStorageSize);
01420 tNextFree = 0;
01421 szText[tNextFree] = '\0';
01422
01423
01424 usChar = usToFootnotePosition(pFile, ulCharPosStart);
01425 ulCharPos = ulCharPosStart;
01426 ulFileOffset = ulCharPos2FileOffset(ulCharPos);
01427
01428 while (usChar != (USHORT)EOF && ulCharPos != ulCharPosNext &&
01429 (usChar == FOOTNOTE_OR_ENDNOTE ||
01430 usChar == PAR_END ||
01431 usChar == TAB ||
01432 usChar == (USHORT)' ')) {
01433 usChar = usNextChar(pFile, footnote_list,
01434 &ulFileOffset, &ulCharPos, NULL);
01435 }
01436
01437 while (usChar != (USHORT)EOF && ulCharPos != ulCharPosNext) {
01438
01439 if (usChar == START_EMBEDDED) {
01440 bSkip = TRUE;
01441 } else if (usChar == END_IGNORE || usChar == END_EMBEDDED) {
01442 bSkip = FALSE;
01443 }
01444
01445 if (bSkip ||
01446 usChar == END_IGNORE ||
01447 usChar == END_EMBEDDED ||
01448 usChar == FOOTNOTE_OR_ENDNOTE) {
01449 ulChar = IGNORE_CHARACTER;
01450 } else {
01451 ulChar = ulTranslateCharacters(usChar,
01452 ulFileOffset,
01453 iWordVersion,
01454 tOptions.eConversionType,
01455 tOptions.eEncoding,
01456 bOldMacFile);
01457 }
01458
01459 if (ulChar == PICTURE) {
01460 tLen = 5;
01461 strcpy(szResult, "[pic]");
01462 } else if (ulChar == IGNORE_CHARACTER) {
01463 tLen = 0;
01464 szResult[0] = '\0';
01465 } else {
01466 switch (ulChar) {
01467 case PAR_END:
01468 case HARD_RETURN:
01469 case PAGE_BREAK:
01470 case COLUMN_FEED:
01471 ulChar = (ULONG)PAR_END;
01472 break;
01473 case TAB:
01474 ulChar = (ULONG)' ';
01475 break;
01476 default:
01477 break;
01478 }
01479 tLen = tUcs2Utf8(ulChar, szResult, sizeof(szResult));
01480 }
01481
01482 if (tNextFree + tLen + 1 > tStorageSize) {
01483 tStorageSize += EXTENTION_SIZE;
01484 szText = xrealloc(szText, tStorageSize);
01485 }
01486 for (tIndex = 0; tIndex < tLen; tIndex++) {
01487 szText[tNextFree++] = szResult[tIndex];
01488 }
01489 szText[tNextFree] = '\0';
01490
01491 usChar = usNextChar(pFile, footnote_list,
01492 &ulFileOffset, &ulCharPos, NULL);
01493 }
01494
01495 while (tNextFree != 0 && szText[tNextFree - 1] == ' ') {
01496 szText[tNextFree - 1] = '\0';
01497 tNextFree--;
01498 }
01499 if (tNextFree == 0) {
01500
01501 szText = xfree(szText);
01502 return NULL;
01503 }
01504 return szText;
01505 }