d7482997 |
1 | #ifndef HALIBUT_HALIBUT_H |
2 | #define HALIBUT_HALIBUT_H |
3 | |
4 | #include <stdio.h> |
5 | #include <wchar.h> |
6 | #include <time.h> |
7 | |
8 | #ifdef __GNUC__ |
9 | #define NORETURN __attribute__((__noreturn__)) |
10 | #else |
11 | #define NORETURN /* nothing */ |
12 | #endif |
13 | |
14 | #ifndef TRUE |
15 | #define TRUE 1 |
16 | #endif |
17 | #ifndef FALSE |
18 | #define FALSE 0 |
19 | #endif |
20 | |
21 | /* For suppressing unused-parameter warnings */ |
22 | #define IGNORE(x) ( (x) = (x) ) |
23 | |
24 | #include "tree234.h" |
25 | |
26 | /* |
27 | * Structure tags |
28 | */ |
29 | typedef struct input_Tag input; |
30 | typedef struct filepos_Tag filepos; |
31 | typedef struct paragraph_Tag paragraph; |
32 | typedef struct word_Tag word; |
33 | typedef struct keywordlist_Tag keywordlist; |
34 | typedef struct keyword_Tag keyword; |
35 | typedef struct userstyle_Tag userstyle; |
36 | typedef struct numberstate_Tag numberstate; |
37 | typedef struct indexdata_Tag indexdata; |
38 | typedef struct indextag_Tag indextag; |
39 | typedef struct indexentry_Tag indexentry; |
40 | typedef struct macrostack_Tag macrostack; |
41 | |
42 | /* |
43 | * Data structure to hold a file name and index, a line and a |
44 | * column number, for reporting errors |
45 | */ |
46 | struct filepos_Tag { |
47 | char *filename; |
48 | int line, col; |
49 | }; |
50 | |
51 | /* |
52 | * Data structure to hold all the file names etc for input |
53 | */ |
54 | typedef struct pushback_Tag { |
55 | int chr; |
56 | filepos pos; |
57 | } pushback; |
58 | struct input_Tag { |
59 | char **filenames; /* complete list of input files */ |
60 | int nfiles; /* how many in the list */ |
61 | FILE *currfp; /* the currently open one */ |
62 | int currindex; /* which one is that in the list */ |
63 | pushback *pushback; /* pushed-back input characters */ |
64 | int npushback, pushbacksize; |
65 | filepos pos; |
66 | int reportcols; /* report column numbers in errors */ |
67 | macrostack *stack; /* macro expansions in force */ |
68 | }; |
69 | |
70 | /* |
71 | * Data structure to hold the input form of the source, ie a linked |
72 | * list of paragraphs |
73 | */ |
74 | struct paragraph_Tag { |
75 | paragraph *next; |
76 | int type; |
77 | wchar_t *keyword; /* for most special paragraphs */ |
78 | word *words; /* list of words in paragraph */ |
79 | int aux; /* number, in a numbered paragraph |
80 | * or subsection level |
81 | */ |
82 | word *kwtext; /* chapter/section indication */ |
83 | word *kwtext2; /* numeric-only form of kwtext */ |
84 | filepos fpos; |
85 | |
86 | paragraph *parent, *child, *sibling; /* for hierarchy navigation */ |
87 | |
88 | void *private_data; /* for temp use in backends */ |
89 | }; |
90 | enum { |
91 | para_IM, /* index merge */ |
92 | para_BR, /* bibliography rewrite */ |
93 | para_Rule, /* random horizontal rule */ |
94 | para_Chapter, |
95 | para_Appendix, |
96 | para_UnnumberedChapter, |
97 | para_Heading, |
98 | para_Subsect, |
99 | para_Normal, |
100 | para_Biblio, /* causes no output unless turned ... */ |
101 | para_BiblioCited, /* ... into this paragraph type */ |
102 | para_Bullet, |
103 | para_NumberedList, |
7136a6c7 |
104 | para_DescribedThing, |
105 | para_Description, |
d7482997 |
106 | para_Code, |
107 | para_Copyright, |
d7482997 |
108 | para_NoCite, |
109 | para_Title, |
110 | para_VersionID, |
111 | para_Config, /* configuration directive */ |
7136a6c7 |
112 | para_LcontPush, /* begin continuation of list item */ |
113 | para_LcontPop, /* end continuation of list item */ |
2614b01d |
114 | para_QuotePush, /* begin block quote */ |
115 | para_QuotePop, /* end block quote */ |
d7482997 |
116 | para_NotParaType /* placeholder value */ |
117 | }; |
118 | |
119 | /* |
120 | * Data structure to hold an individual word |
121 | */ |
122 | struct word_Tag { |
123 | word *next, *alt; |
124 | int type; |
125 | int aux; |
126 | int breaks; /* can a line break after it? */ |
127 | wchar_t *text; |
128 | filepos fpos; |
129 | }; |
130 | enum { |
131 | /* ORDERING CONSTRAINT: these normal-word types ... */ |
132 | word_Normal, |
133 | word_Emph, |
134 | word_Code, /* monospaced; `quoted' in text */ |
135 | word_WeakCode, /* monospaced, normal in text */ |
136 | /* ... must be in the same order as these space types ... */ |
137 | word_WhiteSpace, /* text is NULL or ignorable */ |
138 | word_EmphSpace, /* WhiteSpace when emphasised */ |
139 | word_CodeSpace, /* WhiteSpace when code */ |
140 | word_WkCodeSpace, /* WhiteSpace when weak code */ |
141 | /* ... and must be in the same order as these quote types ... */ |
142 | word_Quote, /* text is NULL or ignorable */ |
143 | word_EmphQuote, /* Quote when emphasised */ |
144 | word_CodeQuote, /* (can't happen) */ |
145 | word_WkCodeQuote, /* (can't happen) */ |
146 | /* END ORDERING CONSTRAINT */ |
147 | word_internal_endattrs, |
148 | word_UpperXref, /* \K */ |
149 | word_LowerXref, /* \k */ |
150 | word_XrefEnd, /* (invisible; no text) */ |
151 | word_IndexRef, /* (always an invisible one) */ |
152 | word_HyperLink, /* (invisible) */ |
153 | word_HyperEnd /* (also invisible; no text) */ |
154 | }; |
155 | /* aux values for attributed words */ |
156 | enum { |
157 | attr_Only = 0x0000, /* a lone word with the attribute */ |
158 | attr_First = 0x0001, /* the first of a series */ |
159 | attr_Last = 0x0002, /* the last of a series */ |
160 | attr_Always = 0x0003, /* any other part of a series */ |
161 | attr_mask = 0x0003, |
162 | }; |
163 | /* aux values for quote-type words */ |
164 | enum { |
165 | quote_Open = 0x0010, |
166 | quote_Close = 0x0020, |
167 | quote_mask = 0x0030, |
168 | }; |
169 | #define isattr(x) ( ( (x) > word_Normal && (x) < word_WhiteSpace ) || \ |
170 | ( (x) > word_WhiteSpace && (x) < word_internal_endattrs ) ) |
171 | #define sameattr(x,y) ( (((x)-(y)) & 3) == 0 ) |
172 | #define towordstyle(x) ( word_Normal + ((x) & 3) ) |
173 | #define tospacestyle(x) ( word_WhiteSpace + ((x) & 3) ) |
174 | #define toquotestyle(x) ( word_Quote + ((x) & 3) ) |
175 | #define removeattr(x) ( word_Normal + ((x) &~ 3) ) |
176 | |
177 | #define attraux(x) ( (x) & attr_mask ) |
178 | #define quoteaux(x) ( (x) & quote_mask ) |
179 | |
180 | /* |
181 | * error.c |
182 | */ |
183 | void fatal(int code, ...) NORETURN; |
184 | void error(int code, ...); |
185 | enum { |
186 | err_nomemory, /* out of memory */ |
187 | err_optnoarg, /* option `-%s' requires an argument */ |
188 | err_nosuchopt, /* unrecognised option `-%s' */ |
189 | err_noinput, /* no input files */ |
190 | err_cantopen, /* unable to open input file `%s' */ |
191 | err_nodata, /* no data in input files */ |
192 | err_brokencodepara, /* line in codepara didn't begin `\c' */ |
193 | err_kwunclosed, /* expected `}' after keyword */ |
194 | err_kwillegal, /* paragraph type expects no keyword */ |
195 | err_kwexpected, /* paragraph type expects a keyword */ |
196 | err_kwtoomany, /* paragraph type expects only 1 */ |
197 | err_bodyillegal, /* paragraph type expects only kws! */ |
198 | err_badparatype, /* invalid command at start of para */ |
199 | err_badmidcmd, /* invalid command in mid-para */ |
200 | err_unexbrace, /* unexpected brace */ |
201 | err_explbr, /* expected `{' after command */ |
202 | err_commenteof, /* EOF inside braced comment */ |
203 | err_kwexprbr, /* expected `}' after cross-ref */ |
204 | err_missingrbrace, /* unclosed braces at end of para */ |
7136a6c7 |
205 | err_missingrbrace2, /* unclosed braces at end of file */ |
d7482997 |
206 | err_nestedstyles, /* unable to nest text styles */ |
207 | err_nestedindex, /* unable to nest `\i' thingys */ |
208 | err_nosuchkw, /* unresolved cross-reference */ |
209 | err_multiBR, /* multiple \BRs on same keyword */ |
210 | err_nosuchidxtag, /* \IM on unknown index tag (warning) */ |
211 | err_cantopenw, /* can't open output file for write */ |
212 | err_macroexists, /* this macro already exists */ |
213 | err_sectjump, /* jump a heading level, eg \C -> \S */ |
214 | err_winhelp_ctxclash, /* WinHelp context ID hash clash */ |
215 | err_multikw, /* keyword clash in sections */ |
7136a6c7 |
216 | err_misplacedlcont, /* \lcont not after a list item */ |
2614b01d |
217 | err_sectmarkerinblock, /* section marker appeared in block */ |
d7482997 |
218 | err_whatever /* random error of another type */ |
219 | }; |
220 | |
221 | /* |
222 | * malloc.c |
223 | */ |
224 | #ifdef LOGALLOC |
225 | void *smalloc(char *file, int line, int size); |
226 | void *srealloc(char *file, int line, void *p, int size); |
227 | void sfree(char *file, int line, void *p); |
228 | #define smalloc(x) smalloc(__FILE__, __LINE__, x) |
229 | #define srealloc(x, y) srealloc(__FILE__, __LINE__, x, y) |
230 | #define sfree(x) sfree(__FILE__, __LINE__, x) |
231 | #else |
232 | void *smalloc(int size); |
233 | void *srealloc(void *p, int size); |
234 | void sfree(void *p); |
235 | #endif |
236 | void free_word_list(word *w); |
237 | void free_para_list(paragraph *p); |
238 | word *dup_word_list(word *w); |
239 | char *dupstr(char *s); |
240 | |
241 | #define mknew(type) ( (type *) smalloc (sizeof (type)) ) |
242 | #define mknewa(type, number) ( (type *) smalloc ((number) * sizeof (type)) ) |
243 | #define resize(array, len) ( srealloc ((array), (len) * sizeof (*(array))) ) |
244 | #define lenof(array) ( sizeof(array) / sizeof(*(array)) ) |
245 | |
246 | /* |
247 | * ustring.c |
248 | */ |
249 | wchar_t *ustrdup(wchar_t *s); |
250 | char *ustrtoa(wchar_t *s, char *outbuf, int size); |
251 | int ustrlen(wchar_t *s); |
252 | wchar_t *uadv(wchar_t *s); |
253 | wchar_t *ustrcpy(wchar_t *dest, wchar_t *source); |
254 | wchar_t utolower(wchar_t); |
255 | int ustrcmp(wchar_t *lhs, wchar_t *rhs); |
256 | int ustricmp(wchar_t *lhs, wchar_t *rhs); |
257 | int utoi(wchar_t *); |
258 | int utob(wchar_t *); |
259 | int uisdigit(wchar_t); |
260 | wchar_t *ustrlow(wchar_t *s); |
261 | wchar_t *ustrftime(wchar_t *fmt, struct tm *timespec); |
262 | |
263 | /* |
264 | * help.c |
265 | */ |
266 | void help(void); |
267 | void usage(void); |
268 | void showversion(void); |
269 | |
270 | /* |
271 | * licence.c |
272 | */ |
273 | void licence(void); |
274 | |
275 | /* |
276 | * version.c |
277 | */ |
278 | const char *const version; |
279 | |
280 | /* |
281 | * misc.c |
282 | */ |
283 | typedef struct stackTag *stack; |
284 | stack stk_new(void); |
285 | void stk_free(stack); |
286 | void stk_push(stack, void *); |
287 | void *stk_pop(stack); |
7136a6c7 |
288 | void *stk_top(stack); |
d7482997 |
289 | |
290 | typedef struct tagRdstring rdstring; |
291 | struct tagRdstring { |
292 | int pos, size; |
293 | wchar_t *text; |
294 | }; |
295 | typedef struct tagRdstringc rdstringc; |
296 | struct tagRdstringc { |
297 | int pos, size; |
298 | char *text; |
299 | }; |
300 | extern const rdstring empty_rdstring; |
301 | extern const rdstringc empty_rdstringc; |
302 | void rdadd(rdstring *rs, wchar_t c); |
303 | void rdadds(rdstring *rs, wchar_t *p); |
304 | wchar_t *rdtrim(rdstring *rs); |
305 | void rdaddc(rdstringc *rs, char c); |
306 | void rdaddsc(rdstringc *rs, char *p); |
307 | char *rdtrimc(rdstringc *rs); |
308 | |
309 | int compare_wordlists(word *a, word *b); |
310 | |
311 | void mark_attr_ends(paragraph *sourceform); |
312 | |
313 | typedef struct tagWrappedLine wrappedline; |
314 | struct tagWrappedLine { |
315 | wrappedline *next; |
316 | word *begin, *end; /* first & last words of line */ |
317 | int nspaces; /* number of whitespaces in line */ |
318 | int shortfall; /* how much shorter than max width */ |
319 | }; |
320 | wrappedline *wrap_para(word *, int, int, int (*)(word *)); |
321 | void wrap_free(wrappedline *); |
322 | |
323 | /* |
324 | * input.c |
325 | */ |
326 | paragraph *read_input(input *in, indexdata *idx); |
327 | |
328 | /* |
329 | * keywords.c |
330 | */ |
331 | struct keywordlist_Tag { |
332 | int nkeywords; |
333 | int size; |
334 | tree234 *keys; /* sorted by `key' field */ |
335 | word **looseends; /* non-keyword list element numbers */ |
336 | int nlooseends; |
337 | int looseendssize; |
338 | }; |
339 | struct keyword_Tag { |
340 | wchar_t *key; /* the keyword itself */ |
341 | word *text; /* "Chapter 2", "Appendix Q"... */ |
342 | /* (NB: filepos are not set) */ |
343 | paragraph *para; /* the paragraph referenced */ |
344 | }; |
345 | keyword *kw_lookup(keywordlist *, wchar_t *); |
346 | keywordlist *get_keywords(paragraph *); |
347 | void free_keywords(keywordlist *); |
348 | void subst_keywords(paragraph *, keywordlist *); |
349 | |
350 | /* |
351 | * index.c |
352 | */ |
353 | |
354 | /* |
355 | * Data structure to hold both sides of the index. |
356 | */ |
357 | struct indexdata_Tag { |
358 | tree234 *tags; /* holds type `indextag' */ |
359 | tree234 *entries; /* holds type `indexentry' */ |
360 | }; |
361 | |
362 | /* |
363 | * Data structure to hold an index tag (LHS of index). |
364 | */ |
365 | struct indextag_Tag { |
366 | wchar_t *name; |
367 | word *implicit_text; |
368 | word **explicit_texts; |
369 | int nexplicit, explicit_size; |
370 | int nrefs; |
371 | indexentry **refs; /* array of entries referenced by tag */ |
372 | }; |
373 | |
374 | /* |
375 | * Data structure to hold an index entry (RHS of index). |
376 | */ |
377 | struct indexentry_Tag { |
378 | word *text; |
379 | void *backend_data; /* private to back end */ |
380 | }; |
381 | |
382 | indexdata *make_index(void); |
383 | void cleanup_index(indexdata *); |
384 | /* index_merge takes responsibility for freeing arg 3 iff implicit; never |
385 | * takes responsibility for arg 2 */ |
386 | void index_merge(indexdata *, int is_explicit, wchar_t *, word *); |
387 | void build_index(indexdata *); |
388 | void index_debug(indexdata *); |
389 | indextag *index_findtag(indexdata *idx, wchar_t *name); |
390 | |
391 | /* |
392 | * contents.c |
393 | */ |
394 | numberstate *number_init(void); |
395 | void number_cfg(numberstate *, paragraph *); |
96f3af16 |
396 | word *number_mktext(numberstate *, paragraph *, wchar_t *, int *, int *); |
d7482997 |
397 | void number_free(numberstate *); |
398 | |
399 | /* |
400 | * biblio.c |
401 | */ |
402 | void gen_citations(paragraph *, keywordlist *); |
403 | |
404 | /* |
405 | * style.c |
406 | */ |
407 | struct userstyle_Tag { |
408 | }; |
409 | |
410 | /* |
411 | * bk_text.c |
412 | */ |
413 | void text_backend(paragraph *, keywordlist *, indexdata *); |
414 | |
415 | /* |
416 | * bk_xhtml.c |
417 | */ |
418 | void xhtml_backend(paragraph *, keywordlist *, indexdata *); |
419 | |
420 | /* |
421 | * bk_whlp.c |
422 | */ |
423 | void whlp_backend(paragraph *, keywordlist *, indexdata *); |
424 | |
7136a6c7 |
425 | /* |
426 | * bk_man.c |
427 | */ |
428 | void man_backend(paragraph *, keywordlist *, indexdata *); |
429 | |
d7482997 |
430 | #endif |