1 /*
2 * Copyright (c) 2004 Sasha Vasko <sasha@aftercode.net>
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17 */
18
19 #define LOCAL_DEBUG
20 #define EVENT_TRACE
21
22 #include "../../configure.h"
23 #include "../../libAfterStep/asapp.h"
24 #include <unistd.h>
25 #include "../../libAfterStep/parser.h"
26 #include "../../libAfterConf/afterconf.h"
27
28 #include "ASDocGen.h"
29 #include "xmlproc.h"
30
31 #define TAG_INFO_AND_ID(tagname) #tagname, DOCBOOK_##tagname##_ID
32
33 #define ASFAQ_NAME "afterstep_faq"
34
35 ASDocTagHandlingInfo SupportedDocBookTagInfo[DOCBOOK_SUPPORTED_IDS] =
36 {
37 { TAG_INFO_AND_ID(unknown), NULL, NULL },
38 { TAG_INFO_AND_ID(id), NULL, NULL },
39 { TAG_INFO_AND_ID(arg), start_arg_tag, end_arg_tag },
40 { TAG_INFO_AND_ID(url), NULL, NULL },
41 { TAG_INFO_AND_ID(para), start_para_tag, end_para_tag },
42 { TAG_INFO_AND_ID(term), start_term_tag, end_term_tag },
43 { TAG_INFO_AND_ID(code), start_code_tag, end_code_tag },
44 { TAG_INFO_AND_ID(ulink), start_ulink_tag, end_ulink_tag },
45 { TAG_INFO_AND_ID(title), start_title_tag, end_title_tag },
46 { TAG_INFO_AND_ID(group), start_group_tag, end_group_tag },
47 { TAG_INFO_AND_ID(label), NULL, NULL },
48 { TAG_INFO_AND_ID(width), NULL, NULL },
49 { TAG_INFO_AND_ID(depth), NULL, NULL },
50 { TAG_INFO_AND_ID(align), NULL, NULL },
51 { TAG_INFO_AND_ID(anchor), start_anchor_tag, end_anchor_tag },
52 { TAG_INFO_AND_ID(option), start_option_tag, end_option_tag },
53 { TAG_INFO_AND_ID(choice), NULL, NULL },
54 { TAG_INFO_AND_ID(valign), NULL, NULL },
55 { TAG_INFO_AND_ID(command), start_command_tag, end_command_tag },
56 { TAG_INFO_AND_ID(example), start_example_tag, end_example_tag },
57 { TAG_INFO_AND_ID(linkend), NULL, NULL },
58 { TAG_INFO_AND_ID(section), start_section_tag, end_section_tag },
59 { TAG_INFO_AND_ID(fileref), NULL, NULL },
60 { TAG_INFO_AND_ID(refsect1), start_refsect1_tag, end_refsect1_tag },
61 { TAG_INFO_AND_ID(refsect2), start_refsect1_tag, end_refsect1_tag },
62 { TAG_INFO_AND_ID(emphasis), start_emphasis_tag, end_emphasis_tag },
63 { TAG_INFO_AND_ID(listitem), start_listitem_tag, end_listitem_tag },
64 { TAG_INFO_AND_ID(imagedata), start_imagedata_tag, end_imagedata_tag },
65 { TAG_INFO_AND_ID(formalpara), start_formalpara_tag, end_formalpara_tag },
66 { TAG_INFO_AND_ID(cmdsynopsis), start_cmdsynopsis_tag, end_cmdsynopsis_tag },
67 { TAG_INFO_AND_ID(replaceable), start_emphasis_tag, end_emphasis_tag },
68 { TAG_INFO_AND_ID(mediaobject), NULL, NULL },
69 { TAG_INFO_AND_ID(imageobject), NULL, NULL },
70 { TAG_INFO_AND_ID(variablelist), start_variablelist_tag, end_variablelist_tag },
71 { TAG_INFO_AND_ID(varlistentry), start_varlistentry_tag, end_varlistentry_tag },
72 { TAG_INFO_AND_ID(literallayout), start_literallayout_tag, end_literallayout_tag }
73 };
74
75 /*************************************************************************/
76 xml_elem_t*
find_super_section(xml_elem_t * owner,const char * id)77 find_super_section( xml_elem_t* owner, const char *id )
78 {
79 xml_elem_t* sub ;
80 for( sub = owner->child ; sub != NULL ; sub = sub->next )
81 {
82 Bool match_found = False ;
83 xml_elem_t* attr, *attr_curr ;
84 if( sub->tag_id != DOCBOOK_section_ID )
85 continue;
86 attr = xml_parse_parm(sub->parm, DocBookVocabulary);
87 for( attr_curr = attr ; attr_curr ; attr_curr = attr_curr->next )
88 if( attr_curr->tag_id == DOCBOOK_id_ID )
89 break;
90 match_found = ( attr_curr!= NULL && strncmp( attr_curr->parm, id, strlen(attr_curr->parm)) == 0 ) ;
91 /* LOCAL_DEBUG_OUT( "xml_elem_delete for attr %p", attr ); */
92 xml_elem_delete(NULL, attr);
93
94 if( match_found )
95 return find_super_section( sub, id );
96 }
97 return owner;
98 }
99
100
101
102 void
write_doc_cdata(const char * cdata,int len,ASXMLInterpreterState * state)103 write_doc_cdata( const char *cdata, int len, ASXMLInterpreterState *state )
104 {
105 int i ;
106 if( state->doc_type == DocType_XML ||
107 state->doc_type == DocType_HTML ||
108 state->doc_type == DocType_PHP )
109 {
110 int token_start = 0;
111 Bool special = False ;
112 for( i = 0 ; i < len ; ++i )
113 {
114 if( (!isalnum(cdata[i]) && cdata[i] != '_' && cdata[i] != '(' && cdata[i] != ')') || special )
115 {
116 if( token_start < i )
117 {
118 if( get_flags( state->flags, ASXMLI_InsideLink) )
119 {
120 fwrite( &(cdata[token_start]), 1, i-token_start, state->dest_fp );
121 }else
122 {
123 /* need to try and insert an URL here if token is a keyword */
124 char *token = mystrndup( &(cdata[token_start]), i - token_start );
125 ASHashData hdata ;
126 if( !special && get_hash_item(Links, AS_HASHABLE(token), &(hdata.vptr)) == ASH_Success )
127 {
128 if( state->doc_type == DocType_HTML )
129 fprintf( state->dest_fp, "<A href=\"%s\">%s</A>", hdata.cptr, token );
130 else if( state->doc_type == DocType_PHP )
131 fprintf( state->dest_fp, PHPXrefFormat, "visualdoc",token, hdata.cptr, "" );
132 }else
133 fwrite( token, 1, i-token_start, state->dest_fp );
134 free( token );
135 }
136 }
137 token_start = i+1 ;
138
139 if( cdata[i] == '&' )
140 special = ( translate_special_sequence( &(cdata[i]), len-i, NULL ) != '\0' );
141 else if( cdata[i] == ';' && special )
142 special = False ;
143 switch( cdata[i] )
144 {
145 case '<' : fwrite( "<", 1, 4, state->dest_fp ); break ;
146 case '>' : fwrite( ">", 1, 4, state->dest_fp ); break ;
147 case '"' : fwrite( """, 1, 6, state->dest_fp ); break ;
148 case '&' : if( !special )
149 {
150 fwrite( "&", 1, 5, state->dest_fp );
151 break ;
152 }
153 /* otherwise falling through ! */
154 default:
155 fputc( cdata[i], state->dest_fp );
156 }
157 }
158 }
159 if( i > token_start )
160 fwrite( &(cdata[token_start]), 1, i-token_start, state->dest_fp );
161 }else
162 {
163 for( i = 0 ; i < len ; ++i )
164 {
165 int c_len = 0 ;
166 int c = '\0' ;
167
168 if( cdata[i] == '&' )
169 c = translate_special_sequence( &(cdata[i]), len-i, &c_len ) ;
170 if( c != '\0' )
171 i += c_len-1 ;
172 else
173 c = cdata[i];
174 if( c == '\"' && get_flags( state->flags, ASXMLI_EscapeDQuotes) )
175 fputc( '\"', state->dest_fp );
176 else if ( c == '-' && state->doc_type == DocType_NROFF )
177 fputc( '\\', state->dest_fp );
178 else if ( c == '.' && state->doc_type == DocType_NROFF )
179 fputs( "\\&", state->dest_fp );
180 else if ( c == '\\' && state->doc_type == DocType_NROFF )
181 fputc( '\\', state->dest_fp );
182 else if ( c == 152 /*''*/ && state->doc_type == DocType_NROFF )
183 c = '~';
184 fputc( c, state->dest_fp );
185 }
186 }
187 }
188
189
190 void
convert_xml_tag(xml_elem_t * doc,xml_elem_t ** rparm,ASXMLInterpreterState * state)191 convert_xml_tag( xml_elem_t *doc, xml_elem_t **rparm, ASXMLInterpreterState *state )
192 {
193 xml_elem_t* parm = NULL;
194 xml_elem_t* ptr ;
195 const char *tag_name = doc->tag;
196
197 if( state->doc_type != DocType_XML )
198 {
199 parm = xml_parse_parm(doc->parm, DocBookVocabulary);
200 if( doc->tag_id > 0 && doc->tag_id < DOCBOOK_SUPPORTED_IDS )
201 if( SupportedDocBookTagInfo[doc->tag_id].handle_start_tag )
202 SupportedDocBookTagInfo[doc->tag_id].handle_start_tag( doc, parm, state );
203 }else
204 {
205
206 if( doc->tag_id == DOCBOOK_refsect1_ID )
207 tag_name = SupportedDocBookTagInfo[DOCBOOK_section_ID].tag;
208
209 fprintf( state->dest_fp, "<%s", tag_name );
210 if( doc->parm )
211 {
212 char *ptr = NULL;
213 if( doc->tag_id == DOCBOOK_ulink_ID )
214 ptr = strchr( doc->parm, '#' );
215 if( ptr != NULL )
216 {
217 *ptr = '\0' ;
218 fprintf( state->dest_fp, " %s.html#%s", doc->parm, ptr+1 );
219 *ptr = '#' ;
220 }else
221 fprintf( state->dest_fp, " %s", doc->parm );
222 }
223 fputc( '>', state->dest_fp );
224
225 }
226 for (ptr = doc->child ; ptr ; ptr = ptr->next)
227 {
228 /* LOCAL_DEBUG_OUT( "handling tag's data \"%s\"", ptr->parm ); */
229 if (ptr->tag_id == XML_CDATA_ID )
230 {
231 const char *data_ptr = ptr->parm ;
232 int len = 0 ;
233 if( state->doc_type == DocType_NROFF )
234 {
235 while( data_ptr[0] == '\n' )
236 ++data_ptr ;
237 }
238 len = strlen( data_ptr );
239 if( len > 0 && state->doc_type == DocType_NROFF)
240 {
241 int i ;
242 while( len > 0 && data_ptr[len-1] == '\n' )
243 --len ;
244 /* we want to skip as much whitespace as possible in NROFF */
245 for( i = 0 ; i < len ; ++i )
246 if( !isspace(data_ptr[i]) )
247 break;
248 if( i == len )
249 len = 0 ;
250 else if( !get_flags( state->flags, ASXMLI_LiteralLayout ) )
251 {
252 int from , to ;
253 Bool written = 0 ;
254 for( i = 0 ; i < len ; ++i )
255 {
256 while( isspace(data_ptr[i]) && i < len ) ++i ;
257 from = i ;
258 while( !isspace(data_ptr[i]) && i < len ) ++i ;
259 to = i ;
260 if( to > from )
261 {
262 if( written > 0 )
263 fputc( ' ', state->dest_fp );
264 write_doc_cdata( &data_ptr[from], to-from, state );
265 written += to - from ;
266 }
267 }
268 len = 0 ;
269 }
270 }
271 if( len > 0 )
272 write_doc_cdata( data_ptr, len, state );
273 }else
274 convert_xml_tag( ptr, NULL, state );
275 }
276 /* LOCAL_DEBUG_OUT( "handling end tag with func %p", SupportedDocBookTagInfo[doc->tag_id].handle_end_tag ); */
277 if( state->doc_type != DocType_XML )
278 {
279 if( doc->tag_id > 0 && doc->tag_id < DOCBOOK_SUPPORTED_IDS )
280 if( SupportedDocBookTagInfo[doc->tag_id].handle_end_tag )
281 SupportedDocBookTagInfo[doc->tag_id].handle_end_tag( doc, parm, state );
282 /* LOCAL_DEBUG_OUT( "xml_elem_delete for parm %p", parm ); */
283 if (rparm) *rparm = parm;
284 else xml_elem_delete(NULL, parm);
285 }else
286 {
287 fprintf( state->dest_fp, "</%s>", tag_name );
288 }
289
290 }
291
292 Bool
convert_xml_file(const char * syntax_dir,const char * file,ASXMLInterpreterState * state)293 convert_xml_file( const char *syntax_dir, const char *file, ASXMLInterpreterState *state )
294 {
295 char *source_file ;
296 char *doc_str ;
297 Bool empty_file = False ;
298
299 source_file = make_file_name( syntax_dir, file );
300 doc_str = load_file(source_file);
301 LOCAL_DEBUG_OUT( "file %s loaded", source_file );
302 /*LOCAL_DEBUG_OUT( "file %s loaded into {%s}", source_file, doc_str ); */
303 if( doc_str != NULL )
304 {
305 xml_elem_t* doc;
306 xml_elem_t* ptr;
307
308 if( file[0] == '_' && !get_flags( state->flags, ASXMLI_ProcessingOptions ))
309 state->pre_options_size += strlen(doc_str) ;
310 else
311 set_flags( state->flags, ASXMLI_ProcessingOptions );
312
313 doc = xml_parse_doc(doc_str, DocBookVocabulary);
314 LOCAL_DEBUG_OUT( "file %s parsed, child is %p", source_file, doc->child );
315 if( doc->child )
316 {
317 LOCAL_DEBUG_OUT( "child tag = \"%s\", childs child = %p", doc->child->tag, doc->child->child);
318 empty_file = ( doc->child->tag_id == DOCBOOK_section_ID &&
319 doc->child->child == NULL );
320 if( doc->child->child )
321 {
322 empty_file = ( doc->child->child->tag_id == XML_CDATA_ID && doc->child->child->next == NULL );
323 LOCAL_DEBUG_OUT( "childs child tag = \"%s\", parm = \"%s\"", doc->child->child->tag, doc->child->child->parm);
324 }
325 }
326 LOCAL_DEBUG_OUT( "file %s %s", source_file, empty_file?"empty":"not empty" );
327 if( !empty_file )
328 {
329 for (ptr = doc->child ; ptr ; ptr = ptr->next)
330 {
331 LOCAL_DEBUG_OUT( "converting child <%s>", ptr->tag );
332 convert_xml_tag( ptr, NULL, state );
333 LOCAL_DEBUG_OUT( "done converting child <%s>", ptr->tag );
334 }
335 }
336 /* Delete the xml. */
337 LOCAL_DEBUG_OUT( "deleting xml %p", doc );
338 xml_elem_delete(NULL, doc);
339 LOCAL_DEBUG_OUT( "freeing doc_str %p", doc_str );
340 free( doc_str );
341 }
342 LOCAL_DEBUG_OUT( "done with %s", source_file );
343 free( source_file );
344 fprintf( state->dest_fp, "\n" );
345 return !empty_file;
346 }
347
348 int
check_xml_contents(const char * syntax_dir,const char * file)349 check_xml_contents( const char *syntax_dir, const char *file )
350 {
351 char *source_file ;
352 char *doc_str ;
353 int size = 0 ;
354
355 source_file = make_file_name( syntax_dir, file );
356 doc_str = load_file(source_file);
357 if( doc_str != NULL )
358 {
359 xml_elem_t* doc;
360 size = strlen( doc_str );
361 doc = xml_parse_doc(doc_str, DocBookVocabulary);
362 if( doc->child )
363 {
364 if( doc->child->tag_id == DOCBOOK_section_ID && doc->child->child == NULL )
365 size = 0 ;
366 else if( doc->child->child )
367 {
368 if( doc->child->child->tag_id == XML_CDATA_ID && doc->child->child->next == NULL )
369 size = 0;
370 }
371 }
372 /* Delete the xml. */
373 LOCAL_DEBUG_OUT( "xml_elem_delete for doc %p", doc );
374 xml_elem_delete(NULL, doc);
375 free( doc_str );
376 }
377 free( source_file );
378 return size;
379 }
380
381 /*************************************************************************/
382 void
close_link(ASXMLInterpreterState * state)383 close_link( ASXMLInterpreterState *state )
384 {
385 if( get_flags( state->flags, ASXMLI_InsideLink ) )
386 {
387 if( state->doc_type == DocType_HTML ||
388 (state->doc_type == DocType_PHP && !get_flags(state->flags, ASXMLI_LinkIsLocal)))
389 {
390 fwrite( "</A>", 1, 4, state->dest_fp );
391 }else if( state->doc_type == DocType_PHP )
392 {
393 if ( TopicIndexName == NULL )
394 {
395 fprintf( state->dest_fp, "\",\"%s\",\"%s\",$subunset) ?>", state->curr_url_page, state->display_name);
396 }
397 else
398 {
399 fprintf( state->dest_fp, "\",\"%s\",$srcunset,$subunset) ?>", state->curr_url_page);
400 }
401
402 }
403 clear_flags( state->flags, ASXMLI_InsideLink|ASXMLI_LinkIsLocal|ASXMLI_LinkIsURL );
404 if( state->curr_url_page )
405 free( state->curr_url_page );
406 if( state->curr_url_anchor )
407 free( state->curr_url_anchor );
408 state->curr_url_anchor = state->curr_url_page = NULL ;
409 }
410 }
411
412
413 void
add_anchor(xml_elem_t * attr,ASXMLInterpreterState * state)414 add_anchor( xml_elem_t *attr, ASXMLInterpreterState *state )
415 {
416 while( attr )
417 {
418 if( attr->tag_id == DOCBOOK_id_ID )
419 {
420 close_link(state);
421 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP)
422 fprintf( state->dest_fp, "\n<A NAME=\"%s\">", attr->parm );
423 state->curr_url_anchor = mystrdup(attr->parm);
424 clear_flags( state->flags, ASXMLI_LinkIsLocal|ASXMLI_LinkIsURL );
425 set_flags( state->flags, ASXMLI_InsideLink );
426 break;
427 }
428 attr = attr->next ;
429 }
430
431 }
432
433 void
add_local_link(xml_elem_t * attr,ASXMLInterpreterState * state)434 add_local_link( xml_elem_t *attr, ASXMLInterpreterState *state )
435 {
436 while( attr )
437 {
438 if( attr->tag_id == DOCBOOK_linkend_ID || attr->tag_id == DOCBOOK_url_ID )
439 {
440 char *ptr ;
441 int l ;
442
443 close_link(state);
444 ptr = strchr( attr->parm, '#' );
445 if( ptr != NULL )
446 {
447 *ptr = '\0' ;
448 state->curr_url_page = mystrdup( attr->parm );
449 state->curr_url_anchor = mystrdup( ptr+1 );
450 *ptr = '#' ;
451 }else
452 {
453 state->curr_url_page = mystrdup( attr->parm );
454 state->curr_url_anchor = NULL ;
455 }
456 l = strlen(state->curr_url_page);
457 clear_flags( state->flags, ASXMLI_LinkIsLocal );
458 if( state->curr_url_page[l-1] != '/' &&
459 ( l < 5 || mystrcasecmp( &(state->curr_url_page[l-5]), ".html" ) != 0) &&
460 ( l < 4 || mystrcasecmp( &(state->curr_url_page[l-4]), ".php" ) != 0) &&
461 ( l < 4 || mystrcasecmp( &(state->curr_url_page[l-4]), ".htm" ) != 0) &&
462 ( l < 4 || mystrcasecmp( &(state->curr_url_page[l-4]), ".jpg" ) != 0) &&
463 ( l < 4 || mystrcasecmp( &(state->curr_url_page[l-4]), ".png" ) != 0))
464 {
465 set_flags( state->flags, ASXMLI_LinkIsLocal );
466 }
467
468 if( state->doc_type == DocType_HTML ||
469 (state->doc_type == DocType_PHP && !get_flags( state->flags, ASXMLI_LinkIsLocal )))
470 {
471 fprintf( state->dest_fp, "\n<A href=\"%s", state->curr_url_page );
472 if( get_flags( state->flags, ASXMLI_LinkIsLocal ) )
473 fwrite( ".html", 1, 5, state->dest_fp );
474 if( state->curr_url_anchor != NULL )
475 fprintf( state->dest_fp, "#%s", state->curr_url_anchor );
476 fwrite( "\">", 1, 2, state->dest_fp );
477 }else if( state->doc_type == DocType_PHP )
478 {
479 if (TopicIndexName == NULL) /* added for php part of data catalogue */
480 {
481 fprintf( state->dest_fp, "<? local_doc_url(\"graphics.php\",\"" );
482 }
483 else
484 fprintf( state->dest_fp, "<? local_doc_url(\"visualdoc.php\",\"" );
485 }
486 set_flags( state->flags, ASXMLI_InsideLink|ASXMLI_LinkIsURL );
487 break;
488 }
489 attr = attr->next ;
490 }
491 }
492
493 void
add_glossary_item(xml_elem_t * doc,ASXMLInterpreterState * state)494 add_glossary_item( xml_elem_t* doc, ASXMLInterpreterState *state )
495 {
496 xml_elem_t *cdata = find_tag_by_id( doc->child, XML_CDATA_ID );
497 char *term_text = mystrdup(cdata?cdata->parm:"") ;
498 char *orig_term_text = term_text ;
499 int i ;
500
501 LOCAL_DEBUG_OUT( "term_text = \"%s\"", term_text );
502 while(*term_text)
503 {
504 if( isalnum(*term_text) )
505 break;
506 ++term_text ;
507 }
508 i = 0 ;
509 while( isalnum(term_text[i]) ) ++i ;
510 term_text[i] = '\0' ;
511
512 if( term_text[0] != '\0' ) /* need to add glossary term */
513 {
514 char *target = NULL, *target2 ;
515 char *term = NULL, *term2 ;
516 char *ptr = &(state->dest_file[strlen(state->dest_file)-4]);
517 size_t curr_url_anchor_len = state->curr_url_anchor ? strlen(state->curr_url_anchor) : 0;
518 if( state->doc_type == DocType_PHP && *ptr == '.')
519 *ptr = '\0' ;
520 target = safemalloc( strlen( state->dest_file)+5+1+curr_url_anchor_len+1);
521 sprintf( target, "%s#%s", state->dest_file, state->curr_url_anchor );
522 if( state->doc_type == DocType_PHP && *ptr == '\0' )
523 *ptr = '.' ;
524
525 target2 = mystrdup(target);
526 term2 = mystrdup(term_text);
527 if( add_hash_item( Links, AS_HASHABLE(term2), (void*)target2 ) != ASH_Success )
528 {
529 free( target2 );
530 free( term2 );
531 }
532 term = safemalloc( strlen( term_text)+ 1 + 1 +strlen( state->doc_name ) + 1 +1 );
533 sprintf( term, "%s (%s)", term_text, state->doc_name );
534 LOCAL_DEBUG_OUT( "term = \"%s\"", term );
535 if( add_hash_item( Glossary, AS_HASHABLE(term), (void*)target ) != ASH_Success )
536 {
537 free( target );
538 free( term );
539 }
540 }
541
542 free(orig_term_text);
543 }
544
545 /*************************************************************************/
546 /* DocBook XML tags handlers : */
547 /*************************************************************************/
548
549 void
start_para_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)550 start_para_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
551 {
552 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
553 {
554 close_link(state);
555 fprintf( state->dest_fp, "<P class=\"dense\">" );
556 }else if( state->doc_type == DocType_NROFF )
557 fprintf( state->dest_fp, "\n" );
558
559 }
560
561 void
end_para_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)562 end_para_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
563 {
564 close_link(state);
565 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
566 {
567 fwrite( "</P>", 1, 4, state->dest_fp );
568 }else if( state->doc_type == DocType_NROFF )
569 fprintf( state->dest_fp, "\n" );
570 }
571
572 void
start_formalpara_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)573 start_formalpara_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
574 {
575 add_anchor( parm, state );
576 set_flags( state->flags, ASXMLI_FormalPara );
577 }
578
579 void
end_formalpara_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)580 end_formalpara_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
581 {
582 close_link(state);
583 clear_flags( state->flags, ASXMLI_FormalPara );
584 }
585
586 void
start_command_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)587 start_command_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
588 {
589 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
590 fwrite( "<B>", 1, 3, state->dest_fp );
591 else if( state->doc_type == DocType_NROFF )
592 fprintf( state->dest_fp, " \\fB");
593 }
594
595 void
end_command_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)596 end_command_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
597 {
598 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
599 fwrite( "</B>", 1, 4, state->dest_fp );
600 else if( state->doc_type == DocType_NROFF )
601 fprintf( state->dest_fp, "\\fP ");
602 }
603
604 void
start_emphasis_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)605 start_emphasis_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
606 {
607 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
608 fwrite( "<I>", 1, 3, state->dest_fp );
609 else if( state->doc_type == DocType_NROFF && doc->tag_id != DOCBOOK_replaceable_ID)
610 fprintf( state->dest_fp, " \\fI");
611 }
612
613 void
end_emphasis_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)614 end_emphasis_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
615 {
616 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
617 fwrite( "</I>", 1, 4, state->dest_fp );
618 else if( state->doc_type == DocType_NROFF && doc->tag_id != DOCBOOK_replaceable_ID )
619 fprintf( state->dest_fp, "\\fP ");
620 }
621
622 void
start_literallayout_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)623 start_literallayout_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
624 {
625 close_link(state);
626 set_flags( state->flags, ASXMLI_LiteralLayout );
627 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP)
628 {
629 fprintf( state->dest_fp, "<PRE>");
630 }else if( state->doc_type == DocType_NROFF )
631 fprintf( state->dest_fp, "\n.fi\n");
632 }
633
634 void
end_literallayout_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)635 end_literallayout_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
636 {
637 clear_flags( state->flags, ASXMLI_LiteralLayout );
638 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP)
639 {
640 fwrite( "</PRE>", 1, 6, state->dest_fp );
641 }else if( state->doc_type == DocType_NROFF )
642 fprintf( state->dest_fp, "\n.fi ");
643 }
644
645 void
start_variablelist_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)646 start_variablelist_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
647 {
648 close_link(state);
649 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
650 fprintf( state->dest_fp, "<DL class=\"dense\">" );
651 }
652
653 void
end_variablelist_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)654 end_variablelist_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
655 {
656 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
657 fwrite( "</DL>", 1, 5, state->dest_fp );
658 else if( state->doc_type == DocType_NROFF )
659 fprintf( state->dest_fp, "\n");
660 }
661
662 void
start_varlistentry_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)663 start_varlistentry_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
664 {
665 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
666 add_anchor( parm, state );
667 /* else if( state->doc_type == DocType_NROFF )
668 fprintf( state->dest_fp, "\n.IP "); */
669
670 }
671
672 void
end_varlistentry_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)673 end_varlistentry_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
674 {
675 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
676 close_link(state);
677 // else if( state->doc_type == DocType_NROFF )
678 // fprintf( state->dest_fp, "\n");
679 }
680
681 void
start_term_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)682 start_term_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
683 {
684 #if 1
685 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
686 {
687 if( get_flags( state->flags, ASXMLI_InsideLink ) && state->curr_url_anchor != NULL )
688 {
689 add_glossary_item( doc, state );
690 close_link(state);
691 }
692 }
693 #endif
694 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
695 fprintf( state->dest_fp, "<DT class=\"dense\"><B>" );
696 else if( state->doc_type == DocType_NROFF )
697 {
698 fprintf( state->dest_fp, "\n.IP ");
699 fprintf( state->dest_fp, "\"");
700 set_flags( state->flags, ASXMLI_EscapeDQuotes);
701 }
702 }
703
704 void
end_term_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)705 end_term_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
706 {
707 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
708 fwrite( "</B></DT>", 1, 9, state->dest_fp );
709 else if( state->doc_type == DocType_NROFF )
710 {
711 fprintf( state->dest_fp, "\"\n");
712 clear_flags( state->flags, ASXMLI_EscapeDQuotes);
713 }
714 }
715
716 void
start_listitem_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)717 start_listitem_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
718 {
719 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
720 fprintf( state->dest_fp, "<DD class=\"dense\">" );
721 }
722
723 void
end_listitem_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)724 end_listitem_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
725 {
726 close_link(state);
727 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
728 fwrite( "</DD>", 1, 5, state->dest_fp );
729 }
730
731 void
start_imagedata_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)732 start_imagedata_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
733 {
734 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
735 {
736 const char *url = NULL ;
737 const char *align = NULL ;
738 const char *valign = NULL ;
739 const char *width = NULL ;
740 const char *height = NULL ;
741 while( parm )
742 {
743 switch( parm->tag_id )
744 {
745 case DOCBOOK_width_ID : width = parm->parm ; break ;
746 case DOCBOOK_depth_ID : height = parm->parm ; break ;
747 case DOCBOOK_align_ID : align = parm->parm ; break ;
748 case DOCBOOK_valign_ID : valign = parm->parm ; break ;
749 case DOCBOOK_fileref_ID : url = parm->parm ; break ;
750 }
751 parm = parm->next ;
752 }
753 if( url )
754 {
755 if ( state->doc_type == DocType_PHP )
756 fprintf( state->dest_fp, "<IMG SRC=%s/%s", state->dest_dir, url );
757 else
758 fprintf( state->dest_fp, "<IMG src=\"%s\"", url );
759 if( align != NULL )
760 fprintf( state->dest_fp, " align=\"%s\"", align );
761 if( valign != NULL )
762 fprintf( state->dest_fp, " valign=\"%s\"", valign );
763 if( width != NULL )
764 fprintf( state->dest_fp, " width=\"%s\"", width );
765 if( height != NULL )
766 fprintf( state->dest_fp, " height=\"%s\"", height );
767 fwrite( ">", 1, 1, state->dest_fp );
768 }
769 }
770 }
771
772 void
end_imagedata_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)773 end_imagedata_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
774 {
775 close_link(state);
776 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
777 fwrite( "</IMG>", 1, 6, state->dest_fp );
778 // fprintf( state->dest_fp, "\n", NULL );
779 fputc( '\n', state->dest_fp );
780 }
781
782
783 void
start_section_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)784 start_section_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
785 {
786 ++(state->header_depth);
787 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
788 {
789 /*if( state->doc_type == DocType_HTML )
790 fwrite( "<HR>\n", 1, 5, state->dest_fp );
791 */
792 add_anchor( parm, state );
793 if( get_flags( state->flags, ASXMLI_OrderSections ) )
794 fwrite( "<OL>", 1, 4, state->dest_fp );
795 else
796 fwrite( "<UL>", 1, 4, state->dest_fp );
797 }
798 else if (state->doc_type == DocType_NROFF && !strcmp(state->doc_name, ASFAQ_NAME))
799 {
800 fprintf( state->dest_fp, state->header_depth == 2 ? "\n.SH " : "\n.SS " );
801 }
802 }
803
804 void
end_section_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)805 end_section_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
806 {
807 --(state->header_depth);
808 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
809 {
810 if( get_flags( state->flags, ASXMLI_OrderSections ) )
811 fwrite( "</OL>", 1, 5, state->dest_fp );
812 else
813 fwrite( "</UL>", 1, 5, state->dest_fp );
814 }
815 }
816
817 void
start_refsect1_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)818 start_refsect1_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
819 {
820 ++(state->header_depth);
821 set_flags( state->flags, ASXMLI_RefSection );
822 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
823 {
824 add_anchor( parm, state );
825 fwrite( "<LI>", 1, 4, state->dest_fp );
826 }else if( state->doc_type == DocType_NROFF )
827 fprintf( state->dest_fp, "\n.SH ");
828 }
829
830 void
end_refsect1_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)831 end_refsect1_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
832 {
833 --(state->header_depth);
834 clear_flags( state->flags, ASXMLI_RefSection );
835 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
836 {
837 fwrite( "</LI>", 1, 5, state->dest_fp );
838 }
839 }
840
841 void
start_title_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)842 start_title_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
843 {
844 if( state->doc_type == DocType_HTML )
845 {
846 if( get_flags( state->flags, ASXMLI_FormalPara ) )
847 {
848 add_glossary_item( doc, state );
849 close_link(state);
850 fprintf( state->dest_fp, "<B>" );
851 }else if( get_flags( state->flags, ASXMLI_RefSection ) )
852 fprintf( state->dest_fp, "<p class=\"refsect_header\"><B>" );
853 else
854 fprintf( state->dest_fp, "<p class=\"sect_header\"><B>" );
855 }else if( state->doc_type == DocType_PHP )
856 {
857 if( get_flags( state->flags, ASXMLI_FormalPara ) )
858 {
859 add_glossary_item( doc, state );
860 close_link(state);
861 }
862 fprintf( state->dest_fp, "<B>");
863 }
864 }
865
866 void
end_title_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)867 end_title_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
868 {
869 if( state->doc_type == DocType_HTML )
870 {
871 fprintf( state->dest_fp, "</B>" );
872 if( !get_flags( state->flags, ASXMLI_FormalPara ) )
873 fprintf( state->dest_fp, "</p>");
874 }else if( state->doc_type == DocType_PHP )
875 {
876 fprintf( state->dest_fp, "</B>");
877 if( !get_flags( state->flags, ASXMLI_FormalPara ) )
878 fprintf( state->dest_fp, "<br>");
879 }
880 else if (state->doc_type == DocType_NROFF && !strcmp(state->doc_name, ASFAQ_NAME))
881 {
882 fprintf( state->dest_fp, "\n");
883 }
884 close_link(state);
885 }
886
887 void
start_cmdsynopsis_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)888 start_cmdsynopsis_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
889 {
890 ++(state->header_depth);
891 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
892 {
893 add_anchor( parm, state );
894 if( state->doc_type == DocType_PHP )
895 fprintf( state->dest_fp, "<LI><b>SYNOPSIS</b><p>" );
896 else
897 fprintf( state->dest_fp, "<LI><h%d>SYNOPSIS</h%d>", state->header_depth, state->header_depth );
898 close_link(state);
899 }else if( state->doc_type == DocType_NROFF )
900 fprintf( state->dest_fp, ".SH SYNOPSIS\n");
901 }
902
903 void
end_cmdsynopsis_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)904 end_cmdsynopsis_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
905 {
906 --(state->header_depth);
907 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
908 fwrite( "</LI>", 1, 5, state->dest_fp );
909 else if( state->doc_type == DocType_NROFF )
910 fprintf( state->dest_fp, "\n");
911 }
912
913 int
check_choice(xml_elem_t * parm)914 check_choice( xml_elem_t *parm )
915 {
916 while( parm )
917 {
918 if( parm->tag_id == DOCBOOK_choice_ID )
919 {
920 if( mystrcasecmp( parm->parm, "opt" ) == 0 )
921 return 1;
922 break;
923 }
924 parm = parm->next ;
925 }
926 return 0;
927 }
928
929 void
start_group_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)930 start_group_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
931 {
932 ++(state->group_depth);
933 set_flags(state->flags, ASXMLI_FirstArg );
934 if( state->doc_type == DocType_NROFF )
935 fputc( ' ', state->dest_fp );
936 if( check_choice( parm ) )
937 fputc( '[', state->dest_fp );
938 }
939
940 void
end_group_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)941 end_group_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
942 {
943 --(state->group_depth);
944 if( state->group_depth <= 0 )
945 set_flags(state->flags, ASXMLI_FirstArg );
946 if( check_choice( parm ) )
947 fputc( ']', state->dest_fp );
948 if( state->doc_type == DocType_NROFF )
949 fputc( ' ', state->dest_fp );
950 }
951
952 void
start_arg_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)953 start_arg_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
954 {
955 if( !get_flags(state->flags, ASXMLI_FirstArg ) && state->group_depth > 0 )
956 fwrite( "| ", 1, 2, state->dest_fp );
957 clear_flags(state->flags, ASXMLI_FirstArg );
958 if( state->doc_type == DocType_NROFF )
959 fputc( ' ', state->dest_fp );
960 if( check_choice( parm ) )
961 fputc( '[', state->dest_fp );
962 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
963 fwrite( "<B>", 1, 3, state->dest_fp );
964 else if( state->doc_type == DocType_NROFF )
965 fprintf( state->dest_fp, "\\fI");
966 }
967
968 void
end_arg_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)969 end_arg_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
970 {
971 --(state->group_depth);
972 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
973 fwrite( "</B>", 1, 4, state->dest_fp );
974 else if( state->doc_type == DocType_NROFF )
975 fprintf( state->dest_fp, "\\fP");
976 if( check_choice( parm ) )
977 fputc( ']', state->dest_fp );
978 if( state->doc_type == DocType_NROFF )
979 fputc( ' ', state->dest_fp );
980 }
981
982 void
start_option_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)983 start_option_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
984 {
985 if( state->doc_type == DocType_HTML )
986 fwrite( "<B>", 1, 3, state->dest_fp );
987 }
988
989 void
end_option_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)990 end_option_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
991 {
992 if( state->doc_type == DocType_HTML )
993 fwrite( "</B>", 1, 4, state->dest_fp );
994 }
995
996 void
start_example_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)997 start_example_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
998 {
999 set_flags( state->flags, ASXMLI_InsideExample );
1000 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1001 {
1002 add_anchor( parm, state );
1003 close_link(state);
1004 fprintf( state->dest_fp, "<P class=\"dense\"> <B>Example : </B> " );
1005 fprintf( state->dest_fp, "<div class=\"container\">");
1006 }else if( state->doc_type == DocType_NROFF )
1007 fprintf( state->dest_fp, "\nExample : ");
1008
1009 }
1010
1011 void
end_example_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)1012 end_example_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
1013 {
1014 clear_flags( state->flags, ASXMLI_InsideExample );
1015 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1016 {
1017 fprintf( state->dest_fp, "</div><br></p>");
1018 }
1019 }
1020
1021 void
start_code_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)1022 start_code_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
1023 {
1024 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1025 {
1026 add_anchor( parm, state );
1027 close_link(state);
1028 fprintf( state->dest_fp, "<P class=\"dense\">" );
1029 fprintf( state->dest_fp, "<div class=\"container\">");
1030 }else if( state->doc_type == DocType_NROFF )
1031 fprintf( state->dest_fp, "\n.in +4n\n");
1032
1033 }
1034
1035 void
end_code_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)1036 end_code_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
1037 {
1038 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1039 {
1040 fprintf( state->dest_fp, "</div><br></p>");
1041 }
1042 else if( state->doc_type == DocType_NROFF )
1043 fprintf( state->dest_fp, "\n.in\n");
1044 }
1045
1046
1047 void
start_ulink_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)1048 start_ulink_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
1049 {
1050 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1051 {
1052 add_local_link( parm, state );
1053 }
1054 if( state->doc_type == DocType_NROFF )
1055 fputc( ' ', state->dest_fp );
1056 }
1057
1058 void
end_ulink_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)1059 end_ulink_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
1060 {
1061 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1062 close_link(state);
1063 if( state->doc_type == DocType_NROFF )
1064 fputc( ' ', state->dest_fp );
1065 }
1066
1067 void
start_anchor_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)1068 start_anchor_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
1069 {
1070 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1071 add_anchor( parm, state );
1072 }
1073
1074 void
end_anchor_tag(xml_elem_t * doc,xml_elem_t * parm,ASXMLInterpreterState * state)1075 end_anchor_tag( xml_elem_t *doc, xml_elem_t *parm, ASXMLInterpreterState *state )
1076 {
1077 if( state->doc_type == DocType_HTML || state->doc_type == DocType_PHP )
1078 close_link(state);
1079 }
1080
1081 /*************************************************************************/
1082 void
compile_links(xml_elem_t * doc,ASXMLInterpreterState * state)1083 compile_links( xml_elem_t *doc, ASXMLInterpreterState *state )
1084 {
1085 while( doc )
1086 {
1087
1088 if( doc->child )
1089 compile_links( doc->child, state );
1090 doc = doc->next ;
1091 }
1092
1093 }
1094