1 /*
2 * sectlist.c
3 * Copyright (C) 2001-2004 A.J. van Os; Released under GNU GPL
4 *
5 * Description:
6 * Build, read and destroy list(s) of Word section information
7 */
8
9 #include <stddef.h>
10 #include <string.h>
11 #include "antiword.h"
12
13
14 /*
15 * Private structure to hide the way the information
16 * is stored from the rest of the program
17 */
18 typedef struct section_mem_tag {
19 section_block_type tInfo;
20 ULONG ulCharPos;
21 struct section_mem_tag *pNext;
22 } section_mem_type;
23
24 /* Variables needed to write the Section Information List */
25 static section_mem_type *pAnchor = NULL;
26 static section_mem_type *pSectionLast = NULL;
27
28
29 /*
30 * vDestroySectionInfoList - destroy the Section Information List
31 */
32 void
vDestroySectionInfoList(void)33 vDestroySectionInfoList(void)
34 {
35 section_mem_type *pCurr, *pNext;
36
37 DBG_MSG("vDestroySectionInfoList");
38
39 /* Free the Section Information List */
40 pCurr = pAnchor;
41 while (pCurr != NULL) {
42 pNext = pCurr->pNext;
43 pCurr = xfree(pCurr);
44 pCurr = pNext;
45 }
46 pAnchor = NULL;
47 /* Reset all control variables */
48 pSectionLast = NULL;
49 } /* end of vDestroySectionInfoList */
50
51 /*
52 * vAdd2SectionInfoList - Add an element to the Section Information List
53 */
54 void
vAdd2SectionInfoList(const section_block_type * pSection,ULONG ulCharPos)55 vAdd2SectionInfoList(const section_block_type *pSection, ULONG ulCharPos)
56 {
57 section_mem_type *pListMember;
58
59 fail(pSection == NULL);
60
61 /* Create list member */
62 pListMember = xmalloc(sizeof(section_mem_type));
63 /* Fill the list member */
64 pListMember->tInfo = *pSection;
65 pListMember->ulCharPos = ulCharPos;
66 pListMember->pNext = NULL;
67 /* Add the new member to the list */
68 if (pAnchor == NULL) {
69 pAnchor = pListMember;
70 } else {
71 fail(pSectionLast == NULL);
72 pSectionLast->pNext = pListMember;
73 }
74 pSectionLast = pListMember;
75 } /* vAdd2SectionInfoList */
76
77 /*
78 * vGetDefaultSection - fill the section struct with default values
79 */
80 void
vGetDefaultSection(section_block_type * pSection)81 vGetDefaultSection(section_block_type *pSection)
82 {
83 (void)memset(pSection, 0, sizeof(*pSection));
84 pSection->bNewPage = TRUE;
85 } /* end of vGetDefaultSection */
86
87 /*
88 * vDefault2SectionInfoList - Add a default to the Section Information List
89 */
90 void
vDefault2SectionInfoList(ULONG ulCharPos)91 vDefault2SectionInfoList(ULONG ulCharPos)
92 {
93 section_block_type tSection;
94
95 vGetDefaultSection(&tSection);
96 vAdd2SectionInfoList(&tSection, ulCharPos);
97 } /* end of vDefault2SectionInfoList */
98
99 /*
100 * pGetSectionInfo - get the section information
101 */
102 const section_block_type *
pGetSectionInfo(const section_block_type * pOld,ULONG ulCharPos)103 pGetSectionInfo(const section_block_type *pOld, ULONG ulCharPos)
104 {
105 const section_mem_type *pCurr;
106
107 if (pOld == NULL || ulCharPos == 0) {
108 if (pAnchor == NULL) {
109 /* There are no records, make one */
110 vDefault2SectionInfoList(0);
111 fail(pAnchor == NULL);
112 }
113 /* The first record */
114 NO_DBG_MSG("First record");
115 return &pAnchor->tInfo;
116 }
117
118 NO_DBG_HEX(ulCharPos);
119 for (pCurr = pAnchor; pCurr != NULL; pCurr = pCurr->pNext) {
120 NO_DBG_HEX(pCurr->ulCharPos);
121 if (ulCharPos == pCurr->ulCharPos ||
122 ulCharPos + 1 == pCurr->ulCharPos) {
123 NO_DBG_HEX(pCurr->ulCharPos);
124 return &pCurr->tInfo;
125 }
126 }
127 return pOld;
128 } /* end of pGetSectionInfo */
129
130 /*
131 * tGetNumberOfSections - get the number of sections
132 */
133 size_t
tGetNumberOfSections(void)134 tGetNumberOfSections(void)
135 {
136 const section_mem_type *pCurr;
137 size_t tCounter;
138
139 for (tCounter = 0, pCurr = pAnchor;
140 pCurr != NULL;
141 tCounter++, pCurr = pCurr->pNext)
142 ; /* Empty */
143 return tCounter;
144 } /* end of tGetNumberOfSections */
145
146 /*
147 * ucGetSepHdrFtrSpecification - get the Heder/footer specification
148 */
149 UCHAR
ucGetSepHdrFtrSpecification(size_t tSectionNumber)150 ucGetSepHdrFtrSpecification(size_t tSectionNumber)
151 {
152 const section_mem_type *pCurr;
153 size_t tIndex;
154
155 for (tIndex = 0, pCurr = pAnchor;
156 tIndex < tSectionNumber && pCurr != NULL;
157 tIndex++, pCurr = pCurr->pNext)
158 ; /* Empty */
159 if (pCurr == NULL) {
160 DBG_DEC(tSectionNumber);
161 DBG_FIXME();
162 return 0x00;
163 }
164 return pCurr->tInfo.ucHdrFtrSpecification;
165 } /* end of ucGetSepHdrFtrSpecification */
166