OSDN Git Service

Merge branch 'branch_0.12.0' into branch_0.12.0-svn
[modchxj/mod_chxj.git] / src / chxj_chtml50.c
1 /*
2  * Copyright (C) 2005-2008 Atsushi Konno All rights reserved.
3  * Copyright (C) 2005 QSDN,Inc. All rights reserved.
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  *     http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17 #include <apr_time.h>
18 #include "chxj_chtml50.h"
19 #include "chxj_hdml.h"
20 #include "chxj_str_util.h"
21 #include "chxj_dump.h"
22 #include "chxj_img_conv.h"
23 #include "chxj_qr_code.h"
24 #include "chxj_encoding.h"
25 #include "chxj_header_inf.h"
26
27 #define GET_CHTML50(X) ((chtml50_t *)(X))
28 #undef W_L
29 #undef W_V
30 #define W_L(X)          do { chtml50->out = BUFFERED_WRITE_LITERAL(chtml50->out, &doc->buf, (X)); } while(0)
31 #define W_V(X)          do { chtml50->out = (X) ? BUFFERED_WRITE_VALUE(chtml50->out, &doc->buf, (X))  \
32                                                 : BUFFERED_WRITE_LITERAL(chtml50->out, &doc->buf, ""); } while(0)
33 #undef W_NLCODE
34 #define W_NLCODE()     do { char *nlcode = TO_NLCODE(chtml50->conf); W_V(nlcode); } while (0)
35
36 static char *s_chtml50_start_html_tag     (void *pdoc, Node *node);
37 static char *s_chtml50_end_html_tag       (void *pdoc, Node *node);
38 static char *s_chtml50_start_meta_tag     (void *pdoc, Node *node);
39 static char *s_chtml50_end_meta_tag       (void *pdoc, Node *node);
40 static char *s_chtml50_start_textarea_tag (void *pdoc, Node *node);
41 static char *s_chtml50_end_textarea_tag   (void *pdoc, Node *node);
42 static char *s_chtml50_start_p_tag        (void *pdoc, Node *node);
43 static char *s_chtml50_end_p_tag          (void *pdoc, Node *node);
44 static char *s_chtml50_start_pre_tag      (void *pdoc, Node *node);
45 static char *s_chtml50_end_pre_tag        (void *pdoc, Node *node);
46 static char *s_chtml50_start_h1_tag       (void *pdoc, Node *node);
47 static char *s_chtml50_end_h1_tag         (void *pdoc, Node *node);
48 static char *s_chtml50_start_h2_tag       (void *pdoc, Node *node);
49 static char *s_chtml50_end_h2_tag         (void *pdoc, Node *node);
50 static char *s_chtml50_start_h3_tag       (void *pdoc, Node *node);
51 static char *s_chtml50_end_h3_tag         (void *pdoc, Node *node);
52 static char *s_chtml50_start_h4_tag       (void *pdoc, Node *node);
53 static char *s_chtml50_end_h4_tag         (void *pdoc, Node *node);
54 static char *s_chtml50_start_h5_tag       (void *pdoc, Node *node);
55 static char *s_chtml50_end_h5_tag         (void *pdoc, Node *node);
56 static char *s_chtml50_start_h6_tag       (void *pdoc, Node *node);
57 static char *s_chtml50_end_h6_tag         (void *pdoc, Node *node);
58 static char *s_chtml50_start_ul_tag       (void *pdoc, Node *node);
59 static char *s_chtml50_end_ul_tag         (void *pdoc, Node *node);
60 static char *s_chtml50_start_ol_tag       (void *pdoc, Node *node);
61 static char *s_chtml50_end_ol_tag         (void *pdoc, Node *node);
62 static char *s_chtml50_start_li_tag       (void *pdoc, Node *node);
63 static char *s_chtml50_end_li_tag         (void *pdoc, Node *node);
64 static char *s_chtml50_start_head_tag     (void *pdoc, Node *node);
65 static char *s_chtml50_end_head_tag       (void *pdoc, Node *node);
66 static char *s_chtml50_start_title_tag    (void *pdoc, Node *node);
67 static char *s_chtml50_end_title_tag      (void *pdoc, Node *node);
68 static char *s_chtml50_start_base_tag     (void *pdoc, Node *node);
69 static char *s_chtml50_end_base_tag       (void *pdoc, Node *node);
70 static char *s_chtml50_start_body_tag     (void *pdoc, Node *node);
71 static char *s_chtml50_end_body_tag       (void *pdoc, Node *node);
72 static char *s_chtml50_start_a_tag        (void *pdoc, Node *node);
73 static char *s_chtml50_end_a_tag          (void *pdoc, Node *node);
74 static char *s_chtml50_start_br_tag       (void *pdoc, Node *node);
75 static char *s_chtml50_end_br_tag         (void *pdoc, Node *node);
76 static char *s_chtml50_start_tr_tag       (void *pdoc, Node *node);
77 static char *s_chtml50_end_tr_tag         (void *pdoc, Node *node);
78 static char *s_chtml50_start_font_tag     (void *pdoc, Node *node);
79 static char *s_chtml50_end_font_tag       (void *pdoc, Node *node);
80 static char *s_chtml50_start_form_tag     (void *pdoc, Node *node);
81 static char *s_chtml50_end_form_tag       (void *pdoc, Node *node);
82 static char *s_chtml50_start_input_tag    (void *pdoc, Node *node);
83 static char *s_chtml50_end_input_tag      (void *pdoc, Node *node);
84 static char *s_chtml50_start_center_tag   (void *pdoc, Node *node);
85 static char *s_chtml50_end_center_tag     (void *pdoc, Node *node);
86 static char *s_chtml50_start_hr_tag       (void *pdoc, Node *node);
87 static char *s_chtml50_end_hr_tag         (void *pdoc, Node *node);
88 static char *s_chtml50_start_img_tag      (void *pdoc, Node *node);
89 static char *s_chtml50_end_img_tag        (void *pdoc, Node *node);
90 static char *s_chtml50_start_select_tag   (void *pdoc, Node *node);
91 static char *s_chtml50_end_select_tag     (void *pdoc, Node *node);
92 static char *s_chtml50_start_option_tag   (void *pdoc, Node *node);
93 static char *s_chtml50_end_option_tag     (void *pdoc, Node *node);
94 static char *s_chtml50_start_div_tag      (void *pdoc, Node *node);
95 static char *s_chtml50_end_div_tag        (void *pdoc, Node *node);
96 static char *s_chtml50_chxjif_tag         (void *pdoc, Node *node); 
97 static char *s_chtml50_text_tag           (void *pdoc, Node *node);
98 static char *s_chtml50_start_blockquote_tag(void *pdoc, Node *node);
99 static char *s_chtml50_end_blockquote_tag  (void *pdoc, Node *node);
100 static char *s_chtml50_start_dir_tag      (void *pdoc, Node *node);
101 static char *s_chtml50_end_dir_tag        (void *pdoc, Node *node);
102 static char *s_chtml50_start_dl_tag       (void *pdoc, Node *node);
103 static char *s_chtml50_end_dl_tag         (void *pdoc, Node *node);
104 static char *s_chtml50_start_dt_tag       (void *pdoc, Node *node);
105 static char *s_chtml50_end_dt_tag         (void *pdoc, Node *node);
106 static char *s_chtml50_start_dd_tag       (void *pdoc, Node *node);
107 static char *s_chtml50_end_dd_tag         (void *pdoc, Node *node);
108 static char *s_chtml50_start_marquee_tag  (void *pdoc, Node *node);
109 static char *s_chtml50_end_marquee_tag    (void *pdoc, Node *node);
110 static char *s_chtml50_start_blink_tag    (void *pdoc, Node *node);
111 static char *s_chtml50_end_blink_tag      (void *pdoc, Node *node);
112 static char *s_chtml50_start_menu_tag     (void *pdoc, Node *node);
113 static char *s_chtml50_end_menu_tag       (void *pdoc, Node *node);
114 static char *s_chtml50_start_plaintext_tag       (void *pdoc, Node *node);
115 static char *s_chtml50_start_plaintext_tag_inner (void *pdoc, Node *node);
116 static char *s_chtml50_end_plaintext_tag         (void *pdoc, Node *node);
117 static char *s_chtml50_newline_mark       (void *pdoc, Node *node);
118
119 static void  s_init_chtml50(chtml50_t *chtml, Doc *doc, request_rec *r, device_table *spec);
120
121 static int   s_chtml50_search_emoji(chtml50_t *chtml, char *txt, char **rslt);
122
123
124 tag_handler chtml50_handler[] = {
125   /* tagHTML */
126   {
127     s_chtml50_start_html_tag,
128     s_chtml50_end_html_tag,
129   },
130   /* tagMETA */
131   {
132     s_chtml50_start_meta_tag,
133     s_chtml50_end_meta_tag,
134   },
135   /* tagTEXTAREA */
136   {
137     s_chtml50_start_textarea_tag,
138     s_chtml50_end_textarea_tag,
139   },
140   /* tagP */
141   {
142     s_chtml50_start_p_tag,
143     s_chtml50_end_p_tag,
144   },
145   /* tagPRE */
146   {
147     s_chtml50_start_pre_tag,
148     s_chtml50_end_pre_tag,
149   },
150   /* tagUL */
151   {
152     s_chtml50_start_ul_tag,
153     s_chtml50_end_ul_tag,
154   },
155   /* tagLI */
156   {
157     s_chtml50_start_li_tag,
158     s_chtml50_end_li_tag,
159   },
160   /* tagOL */
161   {
162     s_chtml50_start_ol_tag,
163     s_chtml50_end_ol_tag,
164   },
165   /* tagH1 */
166   {
167     s_chtml50_start_h1_tag,
168     s_chtml50_end_h1_tag,
169   },
170   /* tagH2 */
171   {
172     s_chtml50_start_h2_tag,
173     s_chtml50_end_h2_tag,
174   },
175   /* tagH3 */
176   {
177     s_chtml50_start_h3_tag,
178     s_chtml50_end_h3_tag,
179   },
180   /* tagH4 */
181   {
182     s_chtml50_start_h4_tag,
183     s_chtml50_end_h4_tag,
184   },
185   /* tagH5 */
186   {
187     s_chtml50_start_h5_tag,
188     s_chtml50_end_h5_tag,
189   },
190   /* tagH6 */
191   {
192     s_chtml50_start_h6_tag,
193     s_chtml50_end_h6_tag,
194   },
195   /* tagHEAD */
196   {
197     s_chtml50_start_head_tag,
198     s_chtml50_end_head_tag,
199   },
200   /* tagTITLE */
201   {
202     s_chtml50_start_title_tag,
203     s_chtml50_end_title_tag,
204   },
205   /* tagBASE */
206   {
207     s_chtml50_start_base_tag,
208     s_chtml50_end_base_tag,
209   },
210   /* tagBODY */
211   {
212     s_chtml50_start_body_tag,
213     s_chtml50_end_body_tag,
214   },
215   /* tagA */
216   {
217     s_chtml50_start_a_tag,
218     s_chtml50_end_a_tag,
219   },
220   /* tagBR */
221   {
222     s_chtml50_start_br_tag,
223     s_chtml50_end_br_tag,
224   },
225   /* tagTABLE */
226   {
227     NULL,
228     NULL,
229   },
230   /* tagTR */
231   {
232     s_chtml50_start_tr_tag,
233     s_chtml50_end_tr_tag,
234   },
235   /* tagTD */
236   {
237     NULL,
238     NULL,
239   },
240   /* tagTBODY */
241   {
242     NULL,
243     NULL,
244   },
245   /* tagFONT */
246   {
247     s_chtml50_start_font_tag,
248     s_chtml50_end_font_tag,
249   },
250   /* tagFORM */
251   {
252     s_chtml50_start_form_tag,
253     s_chtml50_end_form_tag,
254   },
255   /* tagINPUT */
256   {
257     s_chtml50_start_input_tag,
258     s_chtml50_end_input_tag,
259   },
260   /* tagCENTER */
261   {
262     s_chtml50_start_center_tag,
263     s_chtml50_end_center_tag,
264   },
265   /* tagHR */
266   {
267     s_chtml50_start_hr_tag,
268     s_chtml50_end_hr_tag,
269   },
270   /* tagIMG */
271   {
272     s_chtml50_start_img_tag,
273     s_chtml50_end_img_tag,
274   },
275   /* tagSELECT */
276   {
277     s_chtml50_start_select_tag,
278     s_chtml50_end_select_tag,
279   },
280   /* tagOPTION */
281   {
282     s_chtml50_start_option_tag,
283     s_chtml50_end_option_tag,
284   },
285   /* tagDIV */
286   {
287     s_chtml50_start_div_tag,
288     s_chtml50_end_div_tag,
289   },
290   /* tagCHXJIF */
291   {
292     s_chtml50_chxjif_tag,
293     NULL,
294   },
295   /* tagNOBR */
296   {
297     NULL,
298     NULL,
299   },
300   /* tagSMALL */
301   {
302     NULL,
303     NULL,
304   },
305   /* tagSTYLE */
306   {
307     NULL,
308     NULL,
309   },
310   /* tagSPAN */
311   {
312     NULL,
313     NULL,
314   },
315   /* tagTEXT */
316   {
317     s_chtml50_text_tag,
318     NULL,
319   },
320   /* tagTH */
321   {
322     NULL,
323     NULL,
324   },
325   /* tagB */
326   {
327     NULL,
328     NULL,
329   },
330   /* tagFIELDSET */
331   {
332     NULL,
333     NULL,
334   },
335   /* tagDT */
336   {
337     s_chtml50_start_dt_tag,
338     s_chtml50_end_dt_tag,
339   },
340   /* tagLEGEND */
341   {
342     NULL,
343     NULL,
344   },
345   /* tagLABEL */
346   {
347     NULL,
348     NULL,
349   },
350   /* tagBLOCKQUOTE */
351   {
352     s_chtml50_start_blockquote_tag,
353     s_chtml50_end_blockquote_tag,
354   },
355   /* tagDIR */
356   {
357     s_chtml50_start_dir_tag,
358     s_chtml50_end_dir_tag,
359   },
360   /* tagDL */
361   {
362     s_chtml50_start_dl_tag,
363     s_chtml50_end_dl_tag,
364   },
365   /* tagDD */
366   {
367     s_chtml50_start_dd_tag,
368     s_chtml50_end_dd_tag,
369   },
370   /* tagMENU */
371   {
372     s_chtml50_start_menu_tag,
373     s_chtml50_end_menu_tag,
374   },
375   /* tagPLAINTEXT */
376   {
377     s_chtml50_start_plaintext_tag,
378     s_chtml50_end_plaintext_tag,
379   },
380   /* tagBLINK */
381   {
382     s_chtml50_start_blink_tag,
383     s_chtml50_end_blink_tag,
384   },
385   /* tagMARQUEE */
386   {
387     s_chtml50_start_marquee_tag,
388     s_chtml50_end_marquee_tag,
389   },
390   /* tagNLMARK */
391   {
392     s_chtml50_newline_mark,
393     NULL,
394   },
395 };
396
397
398 /**
399  * converts from CHTML5.0 to CHTML3.0.
400  *
401  * @param r     [i]   Requet_rec is appointed.
402  * @param spec  [i]   The result of the device specification processing which 
403  *                    was done in advance is appointed.
404  * @param src   [i]   The character string before the converting is appointed.
405  * @return The character string after the converting is returned.
406  */
407 char*
408 chxj_convert_chtml50(
409   request_rec         *r,
410   device_table        *spec,
411   const char          *src,
412   apr_size_t          srclen,
413   apr_size_t          *dstlen,
414   chxjconvrule_entry  *entryp,
415   cookie_t            *cookie
416 )
417 {
418   char      *dst = NULL;
419   char      *ss;
420   chtml50_t chtml50;
421   Doc       doc;
422
423   DBG(r, "start chxj_convert_chtml50()");
424
425   /*--------------------------------------------------------------------------*/
426   /* If qrcode xml                                                            */
427   /*--------------------------------------------------------------------------*/
428   *dstlen = srclen;
429   dst = chxj_qr_code_blob_handler(r, src, (size_t*)dstlen);
430   if (dst) {
431     DBG(r,"i found qrcode xml");
432     DBG(r, "end chxj_convert_chtml50()");
433     return dst;
434   }
435   DBG(r,"not found qrcode xml");
436
437   /*--------------------------------------------------------------------------*/
438   /* The CHTML structure is initialized.                                      */
439   /*--------------------------------------------------------------------------*/
440   s_init_chtml50(&chtml50, &doc, r, spec);
441
442   chtml50.entryp = entryp;
443   chtml50.cookie = cookie;
444
445   chxj_set_content_type(r, chxj_header_inf_set_content_type(r, "text/html; charset=Windows-31J"));
446
447   /*--------------------------------------------------------------------------*/
448   /* The character string of the input is analyzed.                           */
449   /*--------------------------------------------------------------------------*/
450   qs_init_malloc(&doc);
451   qs_init_root_node(&doc);
452
453   ss = apr_pcalloc(r->pool, srclen + 1);
454   memset(ss, 0, srclen + 1);
455   memcpy(ss, src, srclen);
456
457 #ifdef DUMP_LOG
458   chxj_dump_out("[src] CHTML -> CHTML4.0", ss, srclen);
459 #endif
460   chxj_buffered_write_init(r->pool, &doc.buf);
461
462   qs_parse_string(&doc,ss, strlen(ss));
463
464   /*--------------------------------------------------------------------------*/
465   /* It converts it from CHTML to CHTML.                                      */
466   /*--------------------------------------------------------------------------*/
467   chxj_node_convert(spec,r,(void*)&chtml50, &doc, qs_get_root(&doc), 0);
468   chtml50.out = chxj_buffered_write_flush(chtml50.out, &doc.buf);
469   dst = apr_pstrdup(r->pool, chtml50.out);
470   chxj_buffered_write_terminate(&doc.buf);
471
472   qs_all_free(&doc,QX_LOGMARK);
473
474   if (dst == NULL) {
475     dst = apr_pstrdup(r->pool,ss);
476   }
477   if (strlen(dst) == 0) {
478     dst = apr_psprintf(r->pool, "\n");
479   }
480
481   *dstlen = strlen(dst);
482
483 #ifdef DUMP_LOG
484   chxj_dump_out("[src] CHTML -> CHTML4.0", dst, *dstlen);
485 #endif
486
487   DBG(r, "end chxj_convert_chtml50()");
488   return dst;
489 }
490
491
492 /**
493  * The CHTML structure is initialized.
494  *
495  * @param chtml50 [i/o] The pointer to the HDML structure that wants to be
496  *                   initialized is specified.
497  * @param doc   [i]   The Doc structure that should be set to the initialized
498  *                   HDML structure is specified.
499  * @param r     [i]   To use POOL, the pointer to request_rec is specified.
500  * @param spec  [i]   The pointer to the device_table
501  */
502 static void
503 s_init_chtml50(chtml50_t *chtml50, Doc *doc, request_rec *r, device_table *spec)
504 {
505   memset(doc,     0, sizeof(Doc));
506   memset(chtml50, 0, sizeof(chtml50_t));
507
508   doc->r        = r;
509   chtml50->doc  = doc;
510   chtml50->spec = spec;
511   chtml50->out  = qs_alloc_zero_byte_string(r->pool);
512   chtml50->conf = chxj_get_module_config(r->per_dir_config, &chxj_module);
513   chtml50->doc->parse_mode = PARSE_MODE_CHTML;
514 }
515
516
517 /**
518  * Corresponding EMOJI to a current character-code is retrieved. 
519  * The substitution character string is stored in the rslt pointer if agreeing.
520  *
521  * @param chtml50   [i]   The pointer to the CHTML structure is specified. 
522  * @param txt     [i]   The character string to want to examine whether it is 
523  *                      EMOJI is specified. 
524  * @param rslt    [o]   The pointer to the pointer that stores the result is 
525  *                      specified. 
526  * @return When corresponding EMOJI exists, it returns it excluding 0. 
527  */
528 static int
529 s_chtml50_search_emoji(chtml50_t *chtml50, char *txt, char **rslt)
530 {
531   emoji_t       *ee;
532   request_rec   *r;
533   device_table  *spec;
534   int           len;
535
536   spec = chtml50->spec;
537
538   len = strlen(txt);
539   r   = chtml50->doc->r;
540
541   if (!spec) {
542     DBG(r,"spec is NULL");
543   }
544
545   for (ee = chtml50->conf->emoji;
546        ee;
547        ee = ee->next) {
548     if (ee->imode == NULL) {
549       DBG(r, "emoji->imode is NULL");
550       continue;
551     }
552
553     if (ee->imode->string != NULL
554     &&  strlen(ee->imode->string) > 0
555     &&  strncasecmp(ee->imode->string, txt, strlen(ee->imode->string)) == 0) {
556
557       if (spec == NULL || spec->emoji_type == NULL) {
558         *rslt = apr_palloc(r->pool, 3);
559         (*rslt)[0] = ee->imode->hex1byte & 0xff;
560         (*rslt)[1] = ee->imode->hex2byte & 0xff;
561         (*rslt)[2] = 0;
562         return strlen(ee->imode->string);
563       }
564
565       return 0;
566     }
567   }
568
569   return 0;
570 }
571
572
573 /**
574  * It is a handler who processes the HTML tag.
575  *
576  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
577  *                     destination is specified.
578  * @param node   [i]   The HTML tag node is specified.
579  * @return The conversion result is returned.
580  */
581 static char *
582 s_chtml50_start_html_tag(void *pdoc, Node *UNUSED(node)) 
583 {
584   chtml50_t *chtml50 = GET_CHTML50(pdoc);
585   Doc       *doc     = chtml50->doc;
586
587   /*--------------------------------------------------------------------------*/
588   /* start HTML tag                                                           */
589   /*--------------------------------------------------------------------------*/
590   W_L("<html>");
591
592   return chtml50->out;
593 }
594
595
596 /**
597  * It is a handler who processes the HTML tag.
598  *
599  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
600  *                     destination is specified.
601  * @param node   [i]   The HTML tag node is specified.
602  * @return The conversion result is returned.
603  */
604 static char *
605 s_chtml50_end_html_tag(void *pdoc, Node *UNUSED(child)) 
606 {
607   chtml50_t   *chtml50 = GET_CHTML50(pdoc);
608   Doc         *doc     = chtml50->doc;
609
610   W_L("</html>");
611
612   return chtml50->out;
613 }
614
615
616 /**
617  * It is a handler who processes the META tag.
618  *
619  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
620  *                     destination is specified.
621  * @param node   [i]   The META tag node is specified.
622  * @return The conversion result is returned.
623  */
624 static char *
625 s_chtml50_start_meta_tag(void *pdoc, Node *node) 
626 {
627   chtml50_t     *chtml50;
628   Doc           *doc;
629   request_rec   *r;
630   Attr          *attr;
631   int           content_type_flag;
632   int           refresh_flag;
633
634   chtml50 = GET_CHTML50(pdoc);
635   doc     = chtml50->doc;
636   r       = doc->r;
637
638   content_type_flag = 0;
639   refresh_flag      = 0;
640
641   W_L("<meta");
642   /*--------------------------------------------------------------------------*/
643   /* Get Attributes                                                           */
644   /*--------------------------------------------------------------------------*/
645   for (attr = qs_get_attr(doc,node);
646        attr;
647        attr = qs_get_next_attr(doc,attr)) {
648     char *name   = qs_get_attr_name(doc,attr);
649     char *value  = qs_get_attr_value(doc,attr);
650     switch(*name) {
651     case 'h':
652     case 'H':
653       if (strcasecmp(name, "http-equiv") == 0 && value && *value) {
654         /*----------------------------------------------------------------------*/
655         /* CHTML 2.0                                                            */
656         /*----------------------------------------------------------------------*/
657         W_L(" http-equiv=\"");
658         W_V(value);
659         W_L("\"");
660         if (STRCASEEQ('c','C',"content-type", value))
661           content_type_flag = 1;
662   
663         if (STRCASEEQ('r','R',"refresh", value))
664           refresh_flag = 1;
665       }
666       break;
667
668     case 'c':
669     case 'C':
670       if (strcasecmp(name, "content") == 0 && value && *value) {
671         if (content_type_flag) {
672           W_L(" ");
673           W_V(name);
674           W_L("=\"");
675           W_V(chxj_header_inf_set_content_type(r, "text/html; charset=SHIFT_JIS"));
676           W_L("\"");
677         }
678         else
679         if (refresh_flag) {
680           char *buf;
681           char *sec;
682           char *url;
683           buf = apr_pstrdup(r->pool, value);
684           url = strchr(buf, ';');
685           if (url) {
686             sec = apr_pstrdup(r->pool, buf);
687             sec[url-buf] = 0;
688             url++;
689             url = chxj_encoding_parameter(r, url);
690             url = chxj_add_cookie_parameter(r, url, chtml50->cookie);
691             W_L(" ");
692             W_V(name);
693             W_L("=\"");
694             W_V(sec);
695             W_L(";");
696             W_V(url);
697             W_L("\"");
698           }
699         }
700         else {
701           W_L(" ");
702           W_V(name);
703           W_L("=\"");
704           W_V(value);
705           W_L("\"");
706         }
707       }
708       break;
709
710     default:
711       break;
712     }
713   }
714   W_L(">");
715
716   return chtml50->out;
717 }
718
719
720 /**
721  * It is a handler who processes the META tag.
722  *
723  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
724  *                     destination is specified.
725  * @param node   [i]   The META tag node is specified.
726  * @return The conversion result is returned.
727  */
728 static char*
729 s_chtml50_end_meta_tag(void* pdoc, Node* UNUSED(child)) 
730 {
731   chtml50_t *chtml50 = GET_CHTML50(pdoc);
732
733   return chtml50->out;
734 }
735
736
737 /**
738  * It is a handler who processes the HEAD tag.
739  *
740  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
741  *                     destination is specified.
742  * @param node   [i]   The HEAD tag node is specified.
743  * @return The conversion result is returned.
744  */
745 static char*
746 s_chtml50_start_head_tag(void* pdoc, Node* UNUSED(node)) 
747 {
748   chtml50_t   *chtml50 = GET_CHTML50(pdoc);
749   Doc         *doc     = chtml50->doc;
750
751   W_L("<head>");
752
753   return chtml50->out;
754 }
755
756
757 /**
758  * It is a handler who processes the HEAD tag.
759  *
760  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
761  *                     destination is specified.
762  * @param node   [i]   The HEAD tag node is specified.
763  * @return The conversion result is returned.
764  */
765 static char *
766 s_chtml50_end_head_tag(void *pdoc, Node *UNUSED(node)) 
767 {
768   chtml50_t *chtml50 = GET_CHTML50(pdoc);
769   Doc       *doc     = chtml50->doc;
770
771   W_L("</head>");
772
773   return chtml50->out;
774 }
775
776
777 /**
778  * It is a handler who processes the TITLE tag.
779  *
780  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
781  *                     destination is specified.
782  * @param node   [i]   The TITLE tag node is specified.
783  * @return The conversion result is returned.
784  */
785 static char *
786 s_chtml50_start_title_tag(void *pdoc, Node *UNUSED(node)) 
787 {
788   chtml50_t     *chtml50 = GET_CHTML50(pdoc);
789   Doc           *doc     = chtml50->doc;
790
791   W_L("<title>");
792
793   return chtml50->out;
794 }
795
796
797 /**
798  * It is a handler who processes the TITLE tag.
799  *
800  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
801  *                     destination is specified.
802  * @param node   [i]   The TITLE tag node is specified.
803  * @return The conversion result is returned.
804  */
805 static char *
806 s_chtml50_end_title_tag(void *pdoc, Node *UNUSED(child)) 
807 {
808   chtml50_t    *chtml50 = GET_CHTML50(pdoc);
809   Doc          *doc     = chtml50->doc;
810
811   W_L("</title>");
812
813   return chtml50->out;
814 }
815
816
817 /**
818  * It is a handler who processes the BASE tag.
819  *
820  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
821  *                     destination is specified.
822  * @param node   [i]   The BASE tag node is specified.
823  * @return The conversion result is returned.
824  */
825 static char *
826 s_chtml50_start_base_tag(void *pdoc, Node *node) 
827 {
828   Attr        *attr;
829   chtml50_t   *chtml50;
830   Doc         *doc;
831   request_rec *r;
832
833   chtml50 = GET_CHTML50(pdoc);
834   doc     = chtml50->doc;
835   r       = doc->r;
836
837   W_L("<base");
838   /*--------------------------------------------------------------------------*/
839   /* Get Attributes                                                           */
840   /*--------------------------------------------------------------------------*/
841   for (attr = qs_get_attr(doc,node);
842        attr;
843        attr = qs_get_next_attr(doc,attr)) {
844     char *name = qs_get_attr_name(doc,attr);
845     char *value = qs_get_attr_value(doc,attr);
846     if (STRCASEEQ('h','H',"href", name)) {
847       W_L(" href=\"");
848       W_V(value);
849       W_L("\"");
850     }
851   }
852   W_L(">");
853
854   return chtml50->out;
855 }
856
857
858 /**
859  * It is a handler who processes the BASE tag.
860  *
861  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
862  *                     destination is specified.
863  * @param node   [i]   The BASE tag node is specified.
864  * @return The conversion result is returned.
865  */
866 static char *
867 s_chtml50_end_base_tag(void *pdoc, Node *UNUSED(child)) 
868 {
869   chtml50_t *chtml50 = GET_CHTML50(pdoc);
870
871   return chtml50->out;
872 }
873
874
875 /**
876  * It is a handler who processes the BODY tag.
877  *
878  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
879  *                     destination is specified.
880  * @param node   [i]   The BODY tag node is specified.
881  * @return The conversion result is returned.
882  */
883 static char *
884 s_chtml50_start_body_tag(void *pdoc, Node *node) 
885 {
886   chtml50_t   *chtml50;
887   Doc         *doc;
888   request_rec *r;
889   Attr        *attr;
890
891   chtml50 = GET_CHTML50(pdoc);
892   doc     = chtml50->doc;
893   r       = doc->r;
894
895   W_L("<body");
896   /*--------------------------------------------------------------------------*/
897   /* Get Attributes                                                           */
898   /*--------------------------------------------------------------------------*/
899   for (attr = qs_get_attr(doc,node);
900        attr;
901        attr = qs_get_next_attr(doc,attr)) {
902     char *name   = qs_get_attr_name(doc,attr);
903     char *value  = qs_get_attr_value(doc,attr);
904     if (STRCASEEQ('b','B', "bgcolor", name) && value && *value) {
905       /*----------------------------------------------------------------------*/
906       /* CHTML 2.0                                                            */
907       /*----------------------------------------------------------------------*/
908       W_L(" bgcolor=\"");
909       W_V(value);
910       W_L("\"");
911     }
912     else if (STRCASEEQ('t','T', "text", name) && value && *value) {
913       /*----------------------------------------------------------------------*/
914       /* CHTML 2.0                                                            */
915       /*----------------------------------------------------------------------*/
916       W_L(" text=\"");
917       W_V(value);
918       W_L("\"");
919     }
920     else if (STRCASEEQ('l','L',"link", name) && value && *value) {
921       /*----------------------------------------------------------------------*/
922       /* CHTML 2.0                                                            */
923       /*----------------------------------------------------------------------*/
924       W_L(" link=\"");
925       W_V(value);
926       W_L("\"");
927     }
928     else if (STRCASEEQ('a','A',"alink", name) && value && *value) {
929       /*----------------------------------------------------------------------*/
930       /* CHTML 4.0                                                            */
931       /*----------------------------------------------------------------------*/
932       W_L(" alink=\"");
933       W_V(value);
934       W_L("\"");
935     }
936     else if (STRCASEEQ('v','V',"vlink", name) && value && *value) {
937       /*----------------------------------------------------------------------*/
938       /* CHTML 4.0                                                            */
939       /*----------------------------------------------------------------------*/
940       W_L(" vlink=\"");
941       W_V(value);
942       W_L("\"");
943     }
944   }
945   W_L(">");
946
947   return chtml50->out;
948 }
949
950
951 /**
952  * It is a handler who processes the BODY tag.
953  *
954  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
955  *                     destination is specified.
956  * @param node   [i]   The BODY tag node is specified.
957  * @return The conversion result is returned.
958  */
959 static char *
960 s_chtml50_end_body_tag(void *pdoc, Node *UNUSED(child)) 
961 {
962   chtml50_t   *chtml50;
963   Doc         *doc;
964
965   chtml50 = GET_CHTML50(pdoc);
966   doc     = chtml50->doc;
967
968   W_L("</body>");
969
970   return chtml50->out;
971 }
972
973
974 /**
975  * It is a handler who processes the A tag.
976  *
977  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
978  *                     destination is specified.
979  * @param node   [i]   The A tag node is specified.
980  * @return The conversion result is returned.
981  */
982 static char *
983 s_chtml50_start_a_tag(void *pdoc, Node *node) 
984 {
985   chtml50_t     *chtml50;
986   Doc           *doc;
987   request_rec   *r;
988   Attr          *attr;
989
990   chtml50 = GET_CHTML50(pdoc);
991   doc     = chtml50->doc;
992   r       = doc->r;
993
994   W_L("<a");
995   /*--------------------------------------------------------------------------*/
996   /* Get Attributes                                                           */
997   /*--------------------------------------------------------------------------*/
998   for (attr = qs_get_attr(doc,node);
999        attr; 
1000        attr = qs_get_next_attr(doc,attr)) {
1001     char *name  = qs_get_attr_name(doc,attr);
1002     char *value = qs_get_attr_value(doc,attr);
1003     if (STRCASEEQ('n','N',"name", name)) {
1004       /*----------------------------------------------------------------------*/
1005       /* CHTML1.0                                                             */
1006       /*----------------------------------------------------------------------*/
1007       W_L(" name=\"");
1008       W_V(value);
1009       W_L("\"");
1010     }
1011     else if (STRCASEEQ('h','H',"href", name)) {
1012       /*----------------------------------------------------------------------*/
1013       /* CHTML1.0                                                             */
1014       /*----------------------------------------------------------------------*/
1015       value = chxj_encoding_parameter(r, value);
1016       if (! chxj_starts_with(value, "mailto:") && ! chxj_starts_with(value, "telto:")) {
1017         value = chxj_add_cookie_parameter(r, value, chtml50->cookie);
1018       }
1019       W_L(" href=\"");
1020       W_V(value);
1021       W_L("\"");
1022     }
1023     else if (STRCASEEQ('a','A',"accesskey", name)) {
1024       /*----------------------------------------------------------------------*/
1025       /* CHTML1.0                                                             */
1026       /*----------------------------------------------------------------------*/
1027       W_L(" accesskey=\"");
1028       W_V(value);
1029       W_L("\"");
1030     }
1031     else if (STRCASEEQ('c','C',"cti", name)) {
1032       /*----------------------------------------------------------------------*/
1033       /* CHTML 2.0                                                            */
1034       /*----------------------------------------------------------------------*/
1035       W_L(" cti=\"");
1036       W_V(value);
1037       W_L("\"");
1038     }
1039     else if (STRCASEEQ('i','I',"ijam", name)) {
1040       /*----------------------------------------------------------------------*/
1041       /* CHTML 3.0                                                            */
1042       /*----------------------------------------------------------------------*/
1043       /* ignore */
1044     }
1045     else if (STRCASEEQ('u','U',"utn", name)) {
1046       /*----------------------------------------------------------------------*/
1047       /* CHTML 3.0                                                            */
1048       /* It is special only for CHTML.                                        */
1049       /*----------------------------------------------------------------------*/
1050       W_L(" utn ");
1051     }
1052     else if (STRCASEEQ('t','T',"telbook", name)) {
1053       /*----------------------------------------------------------------------*/
1054       /* CHTML 3.0                                                            */
1055       /*----------------------------------------------------------------------*/
1056       /* not support */
1057     }
1058     else if (STRCASEEQ('k','K',"kana", name)) {
1059       /*----------------------------------------------------------------------*/
1060       /* CHTML 3.0                                                            */
1061       /*----------------------------------------------------------------------*/
1062       /* not support */
1063     }
1064     else if (STRCASEEQ('e','E',"email", name)) {
1065       /*----------------------------------------------------------------------*/
1066       /* CHTML 3.0                                                            */
1067       /*----------------------------------------------------------------------*/
1068       /* not support */
1069     }
1070     else if (STRCASEEQ('i','I',"ista", name)) {
1071       /*----------------------------------------------------------------------*/
1072       /* CHTML 4.0                                                            */
1073       /*----------------------------------------------------------------------*/
1074       /* ignore */
1075     }
1076     else if (STRCASEEQ('i','I',"ilet", name)) {
1077       /*----------------------------------------------------------------------*/
1078       /* CHTML 5.0                                                            */
1079       /*----------------------------------------------------------------------*/
1080       /* ignore */
1081     }
1082     else if (STRCASEEQ('i','I',"iswf", name)) {
1083       /*----------------------------------------------------------------------*/
1084       /* CHTML 5.0                                                            */
1085       /*----------------------------------------------------------------------*/
1086       /* ignore */
1087     }
1088     else if (STRCASEEQ('i','I',"irst", name)) {
1089       /*----------------------------------------------------------------------*/
1090       /* CHTML 5.0                                                            */
1091       /*----------------------------------------------------------------------*/
1092       /* ignore */
1093     }
1094   }
1095   W_L(">");
1096   return chtml50->out;
1097 }
1098
1099
1100 /**
1101  * It is a handler who processes the A tag.
1102  *
1103  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1104  *                     destination is specified.
1105  * @param node   [i]   The A tag node is specified.
1106  * @return The conversion result is returned.
1107  */
1108 static char *
1109 s_chtml50_end_a_tag(void *pdoc, Node *UNUSED(child)) 
1110 {
1111   chtml50_t   *chtml50;
1112   Doc         *doc;
1113
1114   chtml50 = GET_CHTML50(pdoc);
1115   doc     = chtml50->doc;
1116
1117   W_L("</a>");
1118
1119   return chtml50->out;
1120 }
1121
1122
1123 /**
1124  * It is a handler who processes the BR tag.
1125  *
1126  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1127  *                     destination is specified.
1128  * @param node   [i]   The BR tag node is specified.
1129  * @return The conversion result is returned.
1130  */
1131 static char *
1132 s_chtml50_start_br_tag(void *pdoc, Node *node)
1133 {
1134   chtml50_t   *chtml50;
1135   Doc         *doc;
1136   request_rec *r;
1137   Attr        *attr;
1138
1139   chtml50 = GET_CHTML50(pdoc);
1140   doc     = chtml50->doc;
1141   r       = doc->r;
1142   W_L("<br");
1143   /*--------------------------------------------------------------------------*/
1144   /* Get Attributes                                                           */
1145   /*--------------------------------------------------------------------------*/
1146   for (attr = qs_get_attr(doc,node);
1147        attr;
1148        attr = qs_get_next_attr(doc,attr)) {
1149     char *name  = qs_get_attr_name(doc,attr);
1150     char *value = qs_get_attr_value(doc,attr);
1151     if (STRCASEEQ('c','C',"clear",name)) {
1152       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('a','A',"all",value))) {
1153         W_L(" clear=\"");
1154         W_V(value);
1155         W_L("\"");
1156       }
1157     }
1158   }
1159   W_L(">");
1160   return chtml50->out;
1161 }
1162
1163
1164 /**
1165  * It is a handler who processes the BR tag.
1166  *
1167  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1168  *                     destination is specified.
1169  * @param node   [i]   The BR tag node is specified.
1170  * @return The conversion result is returned.
1171  */
1172 static char *
1173 s_chtml50_end_br_tag(void *pdoc, Node *UNUSED(child)) 
1174 {
1175   chtml50_t *chtml50 = GET_CHTML50(pdoc);
1176
1177   return chtml50->out;
1178 }
1179
1180
1181 /**
1182  * It is a handler who processes the TR tag.
1183  *
1184  * @param chtml50  [i/o] The pointer to the CHTML structure at the output
1185  *                     destination is specified.
1186  * @param node   [i]   The TR tag node is specified.
1187  * @return The conversion result is returned.
1188  */
1189 static char *
1190 s_chtml50_start_tr_tag(void *pdoc, Node *UNUSED(node)) 
1191 {
1192   chtml50_t *chtml50 = GET_CHTML50(pdoc);
1193
1194   return chtml50->out;
1195 }
1196
1197
1198 /**
1199  * It is a handler who processes the TR tag.
1200  *
1201  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1202  *                     destination is specified.
1203  * @param node   [i]   The TR tag node is specified.
1204  * @return The conversion result is returned.
1205  */
1206 static char *
1207 s_chtml50_end_tr_tag(void *pdoc, Node *UNUSED(child)) 
1208 {
1209   chtml50_t   *chtml50;
1210   Doc         *doc;
1211   request_rec *r;
1212
1213   chtml50 = GET_CHTML50(pdoc);
1214   doc     = chtml50->doc;
1215   r       = doc->r;
1216
1217   W_L("<br>");
1218
1219   return chtml50->out;
1220 }
1221
1222
1223 /**
1224  * It is a handler who processes the FONT tag.
1225  *
1226  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1227  *                     destination is specified.
1228  * @param node   [i]   The FONT tag node is specified.
1229  * @return The conversion result is returned.
1230  */
1231 static char *
1232 s_chtml50_start_font_tag(void *pdoc, Node *node) 
1233 {
1234   Attr          *attr;
1235   chtml50_t     *chtml50;
1236   Doc           *doc;
1237   request_rec   *r;
1238   char          *color = NULL;
1239   char          *size = NULL;
1240
1241   chtml50 = GET_CHTML50(pdoc);
1242   doc     = chtml50->doc;
1243   r       = doc->r;
1244
1245   /*--------------------------------------------------------------------------*/
1246   /* Get Attributes                                                           */
1247   /*--------------------------------------------------------------------------*/
1248   for (attr = qs_get_attr(doc,node);
1249        attr && (color == NULL || size == NULL); 
1250        attr = qs_get_next_attr(doc,attr)) {
1251     char *name  = qs_get_attr_name(doc,attr);
1252     char *value = qs_get_attr_value(doc,attr);
1253     if (STRCASEEQ('c','C',"color", name) && value && *value) {
1254       color = apr_pstrdup(doc->buf.pool, value);
1255     }
1256     else if (STRCASEEQ('s','S',"size", name) && value && *value) {
1257       /*----------------------------------------------------------------------*/
1258       /* CHTML 5.0                                                            */
1259       /*----------------------------------------------------------------------*/
1260       size = apr_pstrdup(doc->buf.pool, value);
1261       switch (*size) {
1262       case '1':
1263       case '2':
1264       case '3':
1265       case '4':
1266       case '5':
1267       case '6':
1268       case '7':
1269         if (*(size + 1) == 0) {
1270           break;
1271         }
1272         size = NULL;
1273         break;
1274
1275       case '+':
1276       case '-':
1277         {
1278           char ch = *(size + 1);
1279           if (ch == '1' || ch == '2' || ch == '3') {
1280             if (*(size + 2) == 0) {
1281               break;
1282             }
1283           }
1284         }
1285         size = NULL;
1286         break;
1287
1288       default:
1289         size = NULL;
1290       }
1291     }
1292     if (color && size) break;
1293   }
1294   if (color || size) {
1295     W_L("<font");
1296     if (color) {
1297       W_L(" color=\"");
1298       W_V(color);
1299       W_L("\"");
1300     }
1301     if (size) {
1302       W_L(" size=\"");
1303       W_V(size);
1304       W_L("\"");
1305     }
1306     W_L(">");
1307     chtml50->font_flag++;
1308   }
1309   return chtml50->out;
1310 }
1311
1312
1313 /**
1314  * It is a handler who processes the FONT tag.
1315  *
1316  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1317  *                     destination is specified.
1318  * @param node   [i]   The FONT tag node is specified.
1319  * @return The conversion result is returned.
1320  */
1321 static char *
1322 s_chtml50_end_font_tag(void *pdoc, Node *UNUSED(child)) 
1323 {
1324   chtml50_t     *chtml50;
1325   Doc           *doc;
1326   request_rec   *r;
1327
1328   chtml50 = GET_CHTML50(pdoc);
1329   doc     = chtml50->doc;
1330   r       = doc->r;
1331
1332   if (chtml50->font_flag) {
1333     W_L("</font>");
1334     chtml50->font_flag--;
1335   }
1336
1337   return chtml50->out;
1338 }
1339
1340
1341 /**
1342  * It is a handler who processes the FORM tag.
1343  *
1344  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1345  *                     destination is specified.
1346  * @param node   [i]   The FORM tag node is specified.
1347  * @return The conversion result is returned.
1348  */
1349 static char *
1350 s_chtml50_start_form_tag(void *pdoc, Node *node) 
1351 {
1352   chtml50_t     *chtml50;
1353   Doc           *doc;
1354   request_rec   *r;
1355   Attr          *attr;
1356   char          *new_hidden_tag = NULL;
1357   char          *attr_method = NULL;
1358   char          *attr_action = NULL;
1359   char          *attr_utn    = NULL;
1360
1361   chtml50 = GET_CHTML50(pdoc);
1362   doc     = chtml50->doc;
1363   r       = doc->r;
1364
1365   /*--------------------------------------------------------------------------*/
1366   /* Get Attributes                                                           */
1367   /*--------------------------------------------------------------------------*/
1368   for (attr = qs_get_attr(doc,node);
1369        attr;
1370        attr = qs_get_next_attr(doc,attr)) {
1371     char *name  = qs_get_attr_name(doc,attr);
1372     char *value = qs_get_attr_value(doc,attr);
1373     if (STRCASEEQ('a','A',"action", name)) {
1374       /*----------------------------------------------------------------------*/
1375       /* CHTML 1.0                                                            */
1376       /*----------------------------------------------------------------------*/
1377       attr_action = chxj_encoding_parameter(r, value);
1378       attr_action = chxj_add_cookie_parameter(r, attr_action, chtml50->cookie);
1379     }
1380     else if (STRCASEEQ('m','M',"method", name)) {
1381       /*----------------------------------------------------------------------*/
1382       /* CHTML 1.0                                                            */
1383       /*----------------------------------------------------------------------*/
1384       attr_method = apr_pstrdup(doc->pool, value);
1385     }
1386     else if (STRCASEEQ('u','U',"utn", name)) {
1387       /*----------------------------------------------------------------------*/
1388       /* CHTML 3.0                                                            */
1389       /* It is special only for CHTML.                                        */
1390       /*----------------------------------------------------------------------*/
1391       attr_utn = value;
1392     }
1393   }
1394
1395   int post_flag = (attr_method && strcasecmp(attr_method, "post") == 0) ? 1 : 0;
1396
1397   W_L("<form");
1398   if (attr_action) {
1399     char *q;
1400     q = strchr(attr_action, '?');
1401     if (q) {
1402       new_hidden_tag = chxj_form_action_to_hidden_tag(r, doc->pool, attr_action, 0, post_flag);
1403       if (new_hidden_tag) {
1404         *q = 0;
1405       }
1406     }
1407     W_L(" action=\"");
1408     W_V(attr_action);
1409     W_L("\"");
1410   }
1411   if (attr_method) {
1412     W_L(" method=\"");
1413     W_V(attr_method);
1414     W_L("\"");
1415   }
1416   if (attr_utn) {
1417     W_L(" utn");
1418   }
1419   W_L(">");
1420   if (new_hidden_tag) {
1421     W_V(new_hidden_tag);
1422   }
1423   return chtml50->out;
1424 }
1425
1426
1427 /**
1428  * It is a handler who processes the FORM tag.
1429  *
1430  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1431  *                     destination is specified.
1432  * @param node   [i]   The FORM tag node is specified.
1433  * @return The conversion result is returned.
1434  */
1435 static char *
1436 s_chtml50_end_form_tag(void *pdoc, Node *UNUSED(child)) 
1437 {
1438   chtml50_t    *chtml50;
1439   Doc          *doc;
1440
1441   chtml50 = GET_CHTML50(pdoc);
1442   doc     = chtml50->doc;
1443
1444   W_L("</form>");
1445
1446   return chtml50->out;
1447 }
1448
1449
1450 /**
1451  * It is a handler who processes the INPUT tag.
1452  *
1453  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1454  *                     destination is specified.
1455  * @param node   [i]   The INPUT tag node is specified.
1456  * @return The conversion result is returned.
1457  */
1458 static char *
1459 s_chtml50_start_input_tag(void *pdoc, Node *node) 
1460 {
1461   chtml50_t   *chtml50;
1462   Doc         *doc;
1463   request_rec *r;
1464   char        *max_length  = NULL;
1465   char        *type        = NULL;
1466   char        *name        = NULL;
1467   char        *value       = NULL;
1468   char        *istyle      = NULL;
1469   char        *size        = NULL;
1470   char        *checked     = NULL;
1471   char        *accesskey   = NULL;
1472
1473   chtml50   = GET_CHTML50(pdoc);
1474   doc       = chtml50->doc;
1475   r         = doc->r;
1476   W_L("<input");
1477   /*--------------------------------------------------------------------------*/
1478   /* Get Attributes                                                           */
1479   /*--------------------------------------------------------------------------*/
1480   type       = qs_get_type_attr(doc, node, doc->buf.pool);
1481   name       = qs_get_name_attr(doc, node, doc->buf.pool);
1482   value      = qs_get_value_attr(doc,node, doc->buf.pool);
1483   istyle     = qs_get_istyle_attr(doc,node,doc->buf.pool);
1484   max_length = qs_get_maxlength_attr(doc,node,doc->buf.pool);
1485   checked    = qs_get_checked_attr(doc,node,doc->buf.pool);
1486   accesskey  = qs_get_accesskey_attr(doc, node, doc->buf.pool);
1487   size       = qs_get_size_attr(doc, node, doc->buf.pool);
1488
1489   if (type) {
1490     type = qs_trim_string(doc->buf.pool, type);
1491     if (type && (STRCASEEQ('t','T',"text",    type) ||
1492                  STRCASEEQ('p','P',"password",type) ||
1493                  STRCASEEQ('c','C',"checkbox",type) ||
1494                  STRCASEEQ('r','R',"radio",   type) ||
1495                  STRCASEEQ('h','H',"hidden",  type) ||
1496                  STRCASEEQ('s','S',"submit",  type) ||
1497                  STRCASEEQ('r','R',"reset",   type))) {
1498       W_L(" type=\"");
1499       W_V(type);
1500       W_L("\"");
1501     }
1502   }
1503   if (size && *size) {
1504     W_L(" size=\"");
1505     W_V(size);
1506     W_L("\"");
1507   }
1508   if (name && *name) {
1509     W_L(" name=\"");
1510     W_V(name);
1511     W_L("\"");
1512   }
1513   if (value && *value) {
1514     W_L(" value=\"");
1515     W_V(chxj_add_slash_to_doublequote(doc->pool, value));
1516     W_L("\"");
1517   }
1518   if (accesskey && *accesskey) {
1519     W_L(" accesskey=\"");
1520     W_V(accesskey);
1521     W_L("\"");
1522   }
1523   if (istyle) {
1524     /*------------------------------------------------------------------------*/
1525     /* CHTML 2.0                                                              */
1526     /*------------------------------------------------------------------------*/
1527     if (*istyle == '1' || *istyle == '2' || *istyle == '3' || *istyle == '4') {
1528       W_L(" istyle=\"");
1529       W_V(istyle);
1530       W_L("\"");
1531     }
1532   }
1533
1534   /*--------------------------------------------------------------------------*/
1535   /* The figure is default for the password.                                  */
1536   /*--------------------------------------------------------------------------*/
1537   if (max_length && *max_length) {
1538     if (chxj_chk_numeric(max_length) != 0) {
1539       max_length = apr_psprintf(r->pool, "0");
1540     }
1541     if (istyle != NULL && *istyle == '1') {
1542       char *vv = apr_psprintf(doc->buf.pool, " maxlength=\"%d\"", chxj_atoi(max_length) * 2);
1543       W_V(vv);
1544     }
1545     else  {
1546       char *vv = apr_psprintf(doc->buf.pool, " maxlength=\"%d\"", chxj_atoi(max_length));
1547       W_V(vv);
1548     }
1549   }
1550   if (checked) {
1551     W_L(" checked");
1552   }
1553   W_L(">");
1554
1555   return chtml50->out;
1556 }
1557
1558
1559 /**
1560  * It is a handler who processes the INPUT tag.
1561  *
1562  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1563  *                     destination is specified.
1564  * @param node   [i]   The INPUT tag node is specified.
1565  * @return The conversion result is returned.
1566  */
1567 static char *
1568 s_chtml50_end_input_tag(void *pdoc, Node *UNUSED(child)) 
1569 {
1570   chtml50_t *chtml50 = GET_CHTML50(pdoc);
1571
1572   return chtml50->out;
1573 }
1574
1575
1576 /**
1577  * It is a handler who processes the CENTER tag.
1578  *
1579  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1580  *                     destination is specified.
1581  * @param node   [i]   The CENTER tag node is specified.
1582  * @return The conversion result is returned.
1583  */
1584 static char *
1585 s_chtml50_start_center_tag(void *pdoc, Node *UNUSED(node)) 
1586 {
1587   chtml50_t     *chtml50;
1588   Doc           *doc;
1589
1590   chtml50 = GET_CHTML50(pdoc);
1591   doc     = chtml50->doc;
1592
1593   W_L("<center>");
1594
1595   return chtml50->out;
1596 }
1597
1598
1599 /**
1600  * It is a handler who processes the CENTER tag.
1601  *
1602  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1603  *                     destination is specified.
1604  * @param node   [i]   The CENTER tag node is specified.
1605  * @return The conversion result is returned.
1606  */
1607 static char *
1608 s_chtml50_end_center_tag(void *pdoc, Node *UNUSED(child)) 
1609 {
1610   chtml50_t     *chtml50;
1611   Doc           *doc;
1612
1613   chtml50 = GET_CHTML50(pdoc);
1614   doc     = chtml50->doc;
1615
1616   W_L("</center>");
1617
1618   return chtml50->out;
1619 }
1620
1621
1622 /**
1623  * It is a handler who processes the HR tag.
1624  *
1625  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1626  *                     destination is specified.
1627  * @param node   [i]   The HR tag node is specified.
1628  * @return The conversion result is returned.
1629  */
1630 static char *
1631 s_chtml50_start_hr_tag(void *pdoc, Node *node) 
1632 {
1633   Attr        *attr;
1634   chtml50_t   *chtml50;
1635   Doc         *doc;
1636   request_rec *r;
1637
1638   chtml50 = GET_CHTML50(pdoc);
1639   doc     = chtml50->doc;
1640   r       = doc->r;
1641
1642   W_L("<hr");
1643  
1644   for (attr = qs_get_attr(doc,node);
1645        attr; 
1646        attr = qs_get_next_attr(doc,attr)) {
1647     char *name = qs_get_attr_name(doc,attr);
1648     char *value = qs_get_attr_value(doc,attr);
1649     if (STRCASEEQ('a','A',"align", name)) {
1650       /*----------------------------------------------------------------------*/
1651       /* CHTML 1.0                                                            */
1652       /*----------------------------------------------------------------------*/
1653       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
1654         W_L(" align=\"");
1655         W_V(value);
1656         W_L("\"");
1657       }
1658     }
1659     else if (STRCASEEQ('s','S',"size", name)) {
1660       /*----------------------------------------------------------------------*/
1661       /* CHTML 1.0                                                            */
1662       /*----------------------------------------------------------------------*/
1663       if (value && *value) {
1664         W_L(" size=\"");
1665         W_V(value);
1666         W_L("\"");
1667       }
1668     }
1669     else if (STRCASEEQ('w','W',"width", name)) {
1670       /*----------------------------------------------------------------------*/
1671       /* CHTML 1.0                                                            */
1672       /*----------------------------------------------------------------------*/
1673       if (value && *value) {
1674         W_L(" width=\"");
1675         W_V(value);
1676         W_L("\"");
1677       }
1678     }
1679     else if (STRCASEEQ('n','N',"noshade", name)) {
1680       /*----------------------------------------------------------------------*/
1681       /* CHTML 1.0                                                            */
1682       /*----------------------------------------------------------------------*/
1683       W_L(" noshade");
1684     }
1685     else if (STRCASEEQ('c','C',"color", name) && value && *value) {
1686       /*----------------------------------------------------------------------*/
1687       /* CHTML 4.0                                                            */
1688       /*----------------------------------------------------------------------*/
1689       W_L(" color=\"");
1690       W_V(value);
1691       W_L("\"");
1692     }
1693   }
1694   W_L(">");
1695
1696   return chtml50->out;
1697 }
1698
1699
1700 /**
1701  * It is a handler who processes the HR tag.
1702  *
1703  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1704  *                     destination is specified.
1705  * @param node   [i]   The HR tag node is specified.
1706  * @return The conversion result is returned.
1707  */
1708 static char *
1709 s_chtml50_end_hr_tag(void *pdoc, Node *UNUSED(child)) 
1710 {
1711   chtml50_t *chtml50 = GET_CHTML50(pdoc);
1712
1713   return chtml50->out;
1714 }
1715
1716
1717 /**
1718  * It is a handler who processes the IMG tag.
1719  *
1720  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1721  *                     destination is specified.
1722  * @param node   [i]   The IMG tag node is specified.
1723  * @return The conversion result is returned.
1724  */
1725 static char *
1726 s_chtml50_start_img_tag(void *pdoc, Node *node) 
1727 {
1728 #ifndef IMG_NOT_CONVERT_FILENAME
1729   device_table *spec;
1730 #endif
1731   chtml50_t    *chtml50;
1732   Doc          *doc;
1733   request_rec  *r;
1734   Attr         *attr;
1735
1736   chtml50 = GET_CHTML50(pdoc);
1737   doc     = chtml50->doc;
1738   r       = doc->r;
1739 #ifndef IMG_NOT_CONVERT_FILENAME
1740   spec    = chtml50->spec;
1741 #endif
1742
1743   W_L("<img");
1744   /*--------------------------------------------------------------------------*/
1745   /* Get Attributes                                                           */
1746   /*--------------------------------------------------------------------------*/
1747   for (attr = qs_get_attr(doc,node);
1748        attr;
1749        attr = qs_get_next_attr(doc,attr)) {
1750     char *name  = qs_get_attr_name(doc,attr);
1751     char *value = qs_get_attr_value(doc,attr);
1752     if (STRCASEEQ('s','S',"src", name)) {
1753       /*----------------------------------------------------------------------*/
1754       /* CHTML 1.0                                                            */
1755       /*----------------------------------------------------------------------*/
1756 #ifdef IMG_NOT_CONVERT_FILENAME
1757       value = chxj_encoding_parameter(r, value);
1758       value = chxj_add_cookie_parameter(r, value, chtml50->cookie);
1759       if (value) {
1760         value = apr_psprintf(r->pool,
1761                              "%s%c%s=true",
1762                              value,
1763                              (strchr(value, '?')) ? '&' : '?',
1764                              CHXJ_COOKIE_NOUPDATE_PARAM);
1765         W_L(" src=\"");
1766         W_V(value);
1767         W_L("\"");
1768       }
1769
1770 #else
1771       value = chxj_img_conv(r,spec,value);
1772       value = chxj_encoding_parameter(r, value);
1773       value = chxj_add_cookie_parameter(r, value, chtml50->cookie);
1774       if (value) {
1775         value = apr_psprintf(r->pool,
1776                              "%s%c%s=true",
1777                              value,
1778                              (strchr(value, '?')) ? '&' : '?',
1779                              CHXJ_COOKIE_NOUPDATE_PARAM);
1780       }
1781       W_L(" src=\"");
1782       W_V(value);
1783       W_L("\"");
1784 #endif
1785     }
1786     else if (STRCASEEQ('a','A',"align", name)) {
1787       /*----------------------------------------------------------------------*/
1788       /* CHTML 1.0                                                            */
1789       /*----------------------------------------------------------------------*/
1790       if (value) {
1791         if (STRCASEEQ('t','T',"top",   value) ||
1792             STRCASEEQ('m','M',"middle",value) ||
1793             STRCASEEQ('b','B',"bottom",value) ||
1794             STRCASEEQ('l','L',"left",  value) ||
1795             STRCASEEQ('c','C',"center",  value) ||
1796             STRCASEEQ('r','R',"right", value)) {
1797           W_L(" align=\"");
1798           W_V(value);
1799           W_L("\"");
1800         }
1801       }
1802     }
1803     else if (STRCASEEQ('w','W',"width", name) && value && *value) {
1804       /*----------------------------------------------------------------------*/
1805       /* CHTML 1.0                                                            */
1806       /*----------------------------------------------------------------------*/
1807       W_L(" width=\"");
1808       W_V(value);
1809       W_L("\"");
1810     }
1811     else if (STRCASEEQ('h','H', "height", name) && value && *value) {
1812       /*----------------------------------------------------------------------*/
1813       /* CHTML 1.0                                                            */
1814       /*----------------------------------------------------------------------*/
1815       W_L(" height=\"");
1816       W_V(value);
1817       W_L("\"");
1818     }
1819     else if (STRCASEEQ('h','H',"hspace", name) && value && *value) {
1820       /*----------------------------------------------------------------------*/
1821       /* CHTML 1.0                                                            */
1822       /*----------------------------------------------------------------------*/
1823       W_L(" hspace=\"");
1824       W_V(value);
1825       W_L("\"");
1826     }
1827     else if (STRCASEEQ('v','V',"vspace", name) && value && *value) {
1828       /*----------------------------------------------------------------------*/
1829       /* CHTML 1.0                                                            */
1830       /*----------------------------------------------------------------------*/
1831       W_L(" vspace=\"");
1832       W_V(value);
1833       W_L("\"");
1834     }
1835     else if (STRCASEEQ('a','A',"alt",name) && value && *value) {
1836       /*----------------------------------------------------------------------*/
1837       /* CHTML 1.0                                                            */
1838       /*----------------------------------------------------------------------*/
1839       W_L(" alt=\"");
1840       W_V(value);
1841       W_L("\"");
1842     }
1843   }
1844   W_L(">");
1845
1846   return chtml50->out;
1847 }
1848
1849
1850 /**
1851  * It is a handler who processes the IMG tag.
1852  *
1853  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1854  *                     destination is specified.
1855  * @param node   [i]   The IMG tag node is specified.
1856  * @return The conversion result is returned.
1857  */
1858 static char *
1859 s_chtml50_end_img_tag(void *pdoc, Node *UNUSED(child)) 
1860 {
1861   chtml50_t *chtml50 = GET_CHTML50(pdoc);
1862
1863   return chtml50->out;
1864 }
1865
1866
1867 /**
1868  * It is a handler who processes the SELECT tag.
1869  *
1870  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1871  *                     destination is specified.
1872  * @param node   [i]   The SELECT tag node is specified.
1873  * @return The conversion result is returned.
1874  */
1875 static char *
1876 s_chtml50_start_select_tag(void *pdoc, Node *child)
1877 {
1878   chtml50_t   *chtml50  = GET_CHTML50(pdoc);
1879   Doc         *doc      = chtml50->doc;
1880   char        *size     = NULL;
1881   char        *name     = NULL;
1882   char        *multiple = NULL;
1883   Attr        *attr;
1884
1885   W_L("<select");
1886   for (attr = qs_get_attr(doc,child);
1887        attr;
1888        attr = qs_get_next_attr(doc,attr)) {
1889     char *nm  = qs_get_attr_name(doc,attr);
1890     char *val = qs_get_attr_value(doc,attr);
1891     if (STRCASEEQ('s','S',"size", nm)) {
1892       /*----------------------------------------------------------------------*/
1893       /* CHTML 1.0 version 2.0                                                */
1894       /*----------------------------------------------------------------------*/
1895       size = apr_pstrdup(doc->buf.pool, val);
1896     }
1897     else if (STRCASEEQ('n','N',"name", nm)) {
1898       /*----------------------------------------------------------------------*/
1899       /* CHTML 1.0 version 2.0                                                */
1900       /*----------------------------------------------------------------------*/
1901       name = apr_pstrdup(doc->buf.pool, val);
1902     }
1903     else if (STRCASEEQ('m','M',"multiple", nm)) {
1904       /*----------------------------------------------------------------------*/
1905       /* CHTML 1.0 version 2.0                                                */
1906       /*----------------------------------------------------------------------*/
1907       multiple = apr_pstrdup(doc->buf.pool, val);
1908     }
1909   }
1910   if (size && *size) {
1911     W_L(" size=\"");
1912     W_V(size);
1913     W_L("\"");
1914   }
1915   if (name && *name) {
1916     W_L(" name=\"");
1917     W_V(name);
1918     W_L("\"");
1919   }
1920   if (multiple) {
1921     W_L(" multiple");
1922   }
1923   W_L(">");
1924
1925   return chtml50->out;
1926 }
1927
1928
1929 /**
1930  * It is a handler who processes the SELECT tag.
1931  *
1932  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1933  *                     destination is specified.
1934  * @param node   [i]   The SELECT tag node is specified.
1935  * @return The conversion result is returned.
1936  */
1937 static char *
1938 s_chtml50_end_select_tag(void *pdoc, Node *UNUSED(child))
1939 {
1940   chtml50_t    *chtml50 = GET_CHTML50(pdoc);
1941   Doc          *doc   = chtml50->doc;
1942
1943   W_L("</select>");
1944
1945   return chtml50->out;
1946 }
1947
1948
1949 /**
1950  * It is a handler who processes the OPTION tag.
1951  *
1952  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
1953  *                     destination is specified.
1954  * @param node   [i]   The OPTION tag node is specified.
1955  * @return The conversion result is returned.
1956  */
1957 static char *
1958 s_chtml50_start_option_tag(void *pdoc, Node *child)
1959 {
1960   Attr        *attr;
1961   chtml50_t   *chtml50;
1962   Doc         *doc;
1963   request_rec *r;
1964   char        *selected;
1965   char        *value;
1966
1967   chtml50    = GET_CHTML50(pdoc);
1968   doc        = chtml50->doc;
1969   r          = doc->r;
1970   selected   = NULL;
1971   value      = NULL;
1972
1973   W_L("<option");
1974   for (attr = qs_get_attr(doc,child);
1975        attr;
1976        attr = qs_get_next_attr(doc,attr)) {
1977     char *nm  = qs_get_attr_name(doc,attr);
1978     char *val = qs_get_attr_value(doc,attr);
1979     if (STRCASEEQ('s','S',"selected", nm)) {
1980       /*----------------------------------------------------------------------*/
1981       /* CHTML 1.0 version 2.0                                                */
1982       /*----------------------------------------------------------------------*/
1983       selected = apr_pstrdup(doc->buf.pool, val);
1984     }
1985     else if (STRCASEEQ('v','V',"value", nm)) {
1986       /*----------------------------------------------------------------------*/
1987       /* CHTML 1.0 version 2.0                                                */
1988       /*----------------------------------------------------------------------*/
1989       value = apr_pstrdup(doc->buf.pool, val);
1990     }
1991   }
1992   if (value && *value) {
1993     W_L(" value=\"");
1994     W_V(value);
1995     W_L("\"");
1996   }
1997   if (selected) {
1998     W_L(" selected");
1999   }
2000   W_L(">");
2001   return chtml50->out;
2002 }
2003
2004
2005 /**
2006  * It is a handler who processes the OPTION tag.
2007  *
2008  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2009  *                     destination is specified.
2010  * @param node   [i]   The OPTION tag node is specified.
2011  * @return The conversion result is returned.
2012  */
2013 static char *
2014 s_chtml50_end_option_tag(void *pdoc, Node *UNUSED(child))
2015 {
2016   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2017
2018   /* Don't close */
2019
2020   return chtml50->out;
2021 }
2022
2023
2024 /**
2025  * It is a handler who processes the DIV tag.
2026  *
2027  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2028  *                     destination is specified.
2029  * @param node   [i]   The DIV tag node is specified.
2030  * @return The conversion result is returned.
2031  */
2032 static char *
2033 s_chtml50_start_div_tag(void *pdoc, Node *child)
2034 {
2035   Attr          *attr;
2036   chtml50_t     *chtml50;
2037   Doc           *doc;
2038   request_rec   *r;
2039   char          *align;
2040
2041   chtml50 = GET_CHTML50(pdoc);
2042   doc     = chtml50->doc;
2043   r       = doc->r;
2044   align   = NULL;
2045
2046   W_L("<div");
2047   for (attr = qs_get_attr(doc,child);
2048        attr;
2049        attr = qs_get_next_attr(doc,attr)) {
2050     char *nm  = qs_get_attr_name(doc,attr);
2051     char *val = qs_get_attr_value(doc,attr);
2052     if (STRCASEEQ('a','A',"align", nm)) {
2053       /*----------------------------------------------------------------------*/
2054       /* CHTML 1.0 (W3C version 3.2)                                          */
2055       /*----------------------------------------------------------------------*/
2056       if (val && (STRCASEEQ('l','L',"left",val) || STRCASEEQ('r','R',"right",val) || STRCASEEQ('c','C',"center",val))) {
2057         align = apr_pstrdup(doc->buf.pool, val);
2058       }
2059     }
2060   }
2061   if (align) {
2062     W_L(" align=\"");
2063     W_V(align);
2064     W_L("\"");
2065   }
2066   W_L(">");
2067
2068   return chtml50->out;
2069 }
2070
2071
2072 /**
2073  * It is a handler who processes the DIV tag.
2074  *
2075  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2076  *                     destination is specified.
2077  * @param node   [i]   The DIV tag node is specified.
2078  * @return The conversion result is returned.
2079  */
2080 static char *
2081 s_chtml50_end_div_tag(void *pdoc, Node *UNUSED(node))
2082 {
2083   chtml50_t    *chtml50 = GET_CHTML50(pdoc);
2084   Doc          *doc     = chtml50->doc;
2085
2086   W_L("</div>");
2087
2088   return chtml50->out;
2089 }
2090
2091
2092 /**
2093  * It is a handler who processes the UL tag.
2094  *
2095  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2096  *                     destination is specified.
2097  * @param node   [i]   The UL tag node is specified.
2098  * @return The conversion result is returned.
2099  */
2100 static char *
2101 s_chtml50_start_ul_tag(void *pdoc, Node *node)
2102 {
2103   chtml50_t   *chtml50 = GET_CHTML50(pdoc);
2104   Doc         *doc     = chtml50->doc;
2105   Attr        *attr;
2106   W_L("<ul");
2107   /*--------------------------------------------------------------------------*/
2108   /* Get Attributes                                                           */
2109   /*--------------------------------------------------------------------------*/
2110   for (attr = qs_get_attr(doc,node);
2111        attr;
2112        attr = qs_get_next_attr(doc,attr)) {
2113     char *name   = qs_get_attr_name(doc,attr);
2114     char *value  = qs_get_attr_value(doc,attr);
2115     if (STRCASEEQ('t','T',"type",name)) {
2116       if (value && (STRCASEEQ('d','D',"disc",value) || STRCASEEQ('c','C',"circle",value) || STRCASEEQ('s','S',"square",value))) {
2117         W_L(" type=\"");
2118         W_V(value);
2119         W_L("\"");
2120       }
2121     }
2122   }
2123   W_L(">");
2124   return chtml50->out;
2125 }
2126
2127
2128 /**
2129  * It is a handler who processes the UL tag.
2130  *
2131  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2132  *                     destination is specified.
2133  * @param node   [i]   The UL tag node is specified.
2134  * @return The conversion result is returned.
2135  */
2136 static char *
2137 s_chtml50_end_ul_tag(void *pdoc, Node *UNUSED(child)) 
2138 {
2139   chtml50_t     *chtml50 = GET_CHTML50(pdoc);
2140   Doc           *doc     = chtml50->doc;
2141
2142   W_L("</ul>");
2143
2144   return chtml50->out;
2145 }
2146
2147
2148 /**
2149  * It is a handler who processes the PRE tag.
2150  *
2151  * @param pdoc  [i/o] The pointer to the XHTML structure at the output
2152  *                     destination is specified.
2153  * @param node   [i]   The PRE tag node is specified.
2154  * @return The conversion result is returned.
2155  */
2156 static char *
2157 s_chtml50_start_pre_tag(void *pdoc, Node *UNUSED(node)) 
2158 {
2159   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2160   Doc       *doc     = chtml50->doc;
2161
2162   chtml50->pre_flag++;
2163   W_L("<pre>");
2164
2165   return chtml50->out;
2166 }
2167
2168
2169 /**
2170  * It is a handler who processes the PRE tag.
2171  *
2172  * @param pdoc  [i/o] The pointer to the XHTML structure at the output
2173  *                     destination is specified.
2174  * @param node   [i]   The PRE tag node is specified.
2175  * @return The conversion result is returned.
2176  */
2177 static char *
2178 s_chtml50_end_pre_tag(void *pdoc, Node *UNUSED(child)) 
2179 {
2180   chtml50_t     *chtml50 = GET_CHTML50(pdoc);
2181   Doc           *doc     = chtml50->doc;
2182
2183   W_L("</pre>");
2184   chtml50->pre_flag--;
2185
2186   return chtml50->out;
2187 }
2188
2189
2190 /**
2191  * It is a handler who processes the P tag.
2192  *
2193  * @param pdoc  [i/o] The pointer to the XHTML structure at the output
2194  *                     destination is specified.
2195  * @param node   [i]   The P tag node is specified.
2196  * @return The conversion result is returned.
2197  */
2198 static char *
2199 s_chtml50_start_p_tag(void *pdoc, Node *node) 
2200 {
2201   chtml50_t     *chtml50;
2202   Doc           *doc;
2203   request_rec   *r;
2204   Attr          *attr;
2205   char          *align = NULL;
2206
2207   chtml50 = GET_CHTML50(pdoc);
2208   doc     = chtml50->doc;
2209   r       = doc->r;
2210
2211   W_L("<p");
2212   for (attr = qs_get_attr(doc,node);
2213        attr;
2214        attr = qs_get_next_attr(doc,attr)) {
2215     char *nm  = qs_get_attr_name(doc,attr);
2216     char *val = qs_get_attr_value(doc,attr);
2217     if (STRCASEEQ('a','A',"align", nm)) {
2218       /*----------------------------------------------------------------------*/
2219       /* CHTML 1.0 (W3C version 3.2)                                          */
2220       /*----------------------------------------------------------------------*/
2221       if (val && (STRCASEEQ('l','L',"left",val) || STRCASEEQ('r','R',"right",val) || STRCASEEQ('c','C',"center",val))) {
2222         align = apr_pstrdup(doc->buf.pool, val);
2223         break;
2224       }
2225     }
2226   }
2227   if (align) {
2228     W_L(" align=\"");
2229     W_V(align);
2230     W_L("\"");
2231   }
2232   W_L(">");
2233   return chtml50->out;
2234 }
2235
2236
2237 /**
2238  * It is a handler who processes the P tag.
2239  *
2240  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2241  *                     destination is specified.
2242  * @param node   [i]   The P tag node is specified.
2243  * @return The conversion result is returned.
2244  */
2245 static char *
2246 s_chtml50_end_p_tag(void *pdoc, Node *UNUSED(child)) 
2247 {
2248   chtml50_t   *chtml50;
2249   Doc         *doc;
2250
2251   chtml50 = GET_CHTML50(pdoc);
2252   doc     = chtml50->doc;
2253
2254   W_L("</p>");
2255
2256   return chtml50->out;
2257 }
2258
2259
2260 /**
2261  * It is a handler who processes the OL tag.
2262  *
2263  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2264  *                     destination is specified.
2265  * @param node   [i]   The OL tag node is specified.
2266  * @return The conversion result is returned.
2267  */
2268 static char *
2269 s_chtml50_start_ol_tag(void *pdoc, Node *node)
2270 {
2271   chtml50_t     *chtml50;
2272   Doc           *doc;
2273   request_rec   *r;
2274   Attr          *attr;
2275
2276   chtml50 = GET_CHTML50(pdoc);
2277   doc     = chtml50->doc;
2278   r       = doc->r;
2279
2280   W_L("<ol");
2281   /*--------------------------------------------------------------------------*/
2282   /* Get Attributes                                                           */
2283   /*--------------------------------------------------------------------------*/
2284   for (attr = qs_get_attr(doc,node);
2285        attr;
2286        attr = qs_get_next_attr(doc,attr)) {
2287     char *name = qs_get_attr_name(doc,attr);
2288     char *value = qs_get_attr_value(doc,attr);
2289     if (STRCASEEQ('t','T',"type",name) && value && (*value == '1' || *value == 'a' || *value == 'A')) {
2290       W_L(" type=\"");
2291       W_V(value);
2292       W_L("\"");
2293     }
2294     else if (STRCASEEQ('s','S',"start",name) && value && *value) {
2295       W_L(" start=\"");
2296       W_V(value);
2297       W_L("\"");
2298     }
2299   }
2300   W_L(">");
2301
2302   return chtml50->out;
2303 }
2304
2305
2306 /**
2307  * It is a handler who processes the OL tag.
2308  *
2309  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2310  *                     destination is specified.
2311  * @param node   [i]   The OL tag node is specified.
2312  * @return The conversion result is returned.
2313  */
2314 static char *
2315 s_chtml50_end_ol_tag(void *pdoc, Node *UNUSED(node)) 
2316 {
2317   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2318   Doc       *doc     = chtml50->doc;
2319
2320   W_L("</ol>");
2321
2322   return chtml50->out;
2323 }
2324
2325
2326 /**
2327  * It is a handler who processes the LI tag.
2328  *
2329  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2330  *                     destination is specified.
2331  * @param node   [i]   The LI tag node is specified.
2332  * @return The conversion result is returned.
2333  */
2334 static char *
2335 s_chtml50_start_li_tag(void *pdoc, Node *node) 
2336 {
2337   chtml50_t   *chtml50 = GET_CHTML50(pdoc);
2338   Doc         *doc     = chtml50->doc;
2339   Attr        *attr;
2340
2341   W_L("<li");
2342   /*--------------------------------------------------------------------------*/
2343   /* Get Attributes                                                           */
2344   /*--------------------------------------------------------------------------*/
2345   for (attr = qs_get_attr(doc,node);
2346        attr;
2347        attr = qs_get_next_attr(doc,attr)) {
2348     char *name = qs_get_attr_name(doc,attr);
2349     char *value = qs_get_attr_value(doc,attr);
2350     if (STRCASEEQ('t','T',"type",name)) {
2351       if (value && (*value == '1' || *value == 'a' || *value == 'A' || STRCASEEQ('d','D',"disc",value) || STRCASEEQ('s','S',"square",value) || STRCASEEQ('c','C',"circle",value))) {
2352         W_L(" type=\"");
2353         W_V(value);
2354         W_L("\"");
2355       }
2356     }
2357     else if (STRCASEEQ('v','V',"value", name) && value && *value) {
2358       W_L(" value=\"");
2359       W_V(value);
2360       W_L("\"");
2361     }
2362   }
2363   W_L(">");
2364   return chtml50->out;
2365 }
2366
2367
2368 /**
2369  * It is a handler who processes the LI tag.
2370  *
2371  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2372  *                     destination is specified.
2373  * @param node   [i]   The LI tag node is specified.
2374  * @return The conversion result is returned.
2375  */
2376 static char *
2377 s_chtml50_end_li_tag(void *pdoc, Node *UNUSED(child)) 
2378 {
2379   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2380
2381   return chtml50->out;
2382 }
2383
2384
2385 /**
2386  * It is a handler who processes the H1 tag.
2387  *
2388  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2389  *                     destination is specified.
2390  * @param node   [i]   The H1 tag node is specified.
2391  * @return The conversion result is returned.
2392  */
2393 static char *
2394 s_chtml50_start_h1_tag(void *pdoc, Node *node)
2395 {
2396   chtml50_t     *chtml50;
2397   Doc           *doc;
2398   request_rec   *r;
2399   Attr          *attr;
2400
2401   chtml50 = GET_CHTML50(pdoc);
2402   doc     = chtml50->doc;
2403   r       = doc->r;
2404
2405   W_L("<h1");
2406   for (attr = qs_get_attr(doc,node);
2407        attr;
2408        attr = qs_get_next_attr(doc,attr)) {
2409     char *name = qs_get_attr_name(doc,attr);
2410     char *value = qs_get_attr_value(doc,attr);
2411     if (STRCASEEQ('a','A',"align", name)) {
2412       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
2413         W_L(" align=\"");
2414         W_V(value);
2415         W_L("\"");
2416         break;
2417       }
2418     }
2419   }
2420   W_L(">");
2421
2422   return chtml50->out;
2423 }
2424
2425
2426 /**
2427  * It is a handler who processes the H1 tag.
2428  *
2429  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2430  *                     destination is specified.
2431  * @param node   [i]   The H1 tag node is specified.
2432  * @return The conversion result is returned.
2433  */
2434 static char *
2435 s_chtml50_end_h1_tag(void *pdoc, Node *UNUSED(child)) 
2436 {
2437   chtml50_t   *chtml50;
2438   Doc         *doc;
2439
2440   chtml50 = GET_CHTML50(pdoc);
2441   doc     = chtml50->doc;
2442
2443   W_L("</h1>");
2444
2445   return chtml50->out;
2446 }
2447
2448
2449 /**
2450  * It is a handler who processes the H2 tag.
2451  *
2452  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2453  *                     destination is specified.
2454  * @param node   [i]   The H2 tag node is specified.
2455  * @return The conversion result is returned.
2456  */
2457 static char *
2458 s_chtml50_start_h2_tag(void *pdoc, Node *node)
2459 {
2460   chtml50_t     *chtml50;
2461   Doc           *doc;
2462   request_rec   *r;
2463   Attr          *attr;
2464
2465   chtml50 = GET_CHTML50(pdoc);
2466   doc     = chtml50->doc;
2467   r       = doc->r;
2468
2469   W_L("<h2");
2470   for (attr = qs_get_attr(doc,node);
2471        attr;
2472        attr = qs_get_next_attr(doc,attr)) {
2473     char *name  = qs_get_attr_name(doc,attr);
2474     char *value = qs_get_attr_value(doc,attr);
2475     if (STRCASEEQ('a','A',"align", name)) {
2476       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
2477         W_L(" align=\"");
2478         W_V(value);
2479         W_L("\"");
2480         break;
2481       }
2482     }
2483   }
2484   W_L(">");
2485   return chtml50->out;
2486 }
2487
2488
2489 /**
2490  * It is a handler who processes the H2 tag.
2491  *
2492  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2493  *                     destination is specified.
2494  * @param node   [i]   The H2 tag node is specified.
2495  * @return The conversion result is returned.
2496  */
2497 static char *
2498 s_chtml50_end_h2_tag(void *pdoc, Node *UNUSED(child)) 
2499 {
2500   chtml50_t   *chtml50 = GET_CHTML50(pdoc);
2501   Doc         *doc     = chtml50->doc;
2502
2503   W_L("</h2>");
2504
2505   return chtml50->out;
2506 }
2507
2508
2509 /**
2510  * It is a handler who processes the H3 tag.
2511  *
2512  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2513  *                     destination is specified.
2514  * @param node   [i]   The H3 tag node is specified.
2515  * @return The conversion result is returned.
2516  */
2517 static char *
2518 s_chtml50_start_h3_tag(void *pdoc, Node *node)
2519 {
2520   chtml50_t   *chtml50;
2521   Doc         *doc;
2522   request_rec *r;
2523   Attr        *attr;
2524
2525   chtml50 = GET_CHTML50(pdoc);
2526   doc     = chtml50->doc;
2527   r       = doc->r;
2528
2529   W_L("<h3");
2530   for (attr = qs_get_attr(doc,node);
2531        attr;
2532        attr = qs_get_next_attr(doc,attr)) {
2533     char *name  = qs_get_attr_name(doc,attr);
2534     char *value = qs_get_attr_value(doc,attr);
2535     if (STRCASEEQ('a','A',"align", name)) {
2536       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
2537         W_L(" align=\"");
2538         W_V(value);
2539         W_L("\"");
2540         break;
2541       }
2542     }
2543   }
2544   W_L(">");
2545
2546   return chtml50->out;
2547 }
2548
2549
2550 /**
2551  * It is a handler who processes the H3 tag.
2552  *
2553  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2554  *                     destination is specified.
2555  * @param node   [i]   The H3 tag node is specified.
2556  * @return The conversion result is returned.
2557  */
2558 static char *
2559 s_chtml50_end_h3_tag(void *pdoc, Node *UNUSED(child))
2560 {
2561   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2562   Doc       *doc   = chtml50->doc;
2563
2564   W_L("</h3>");
2565
2566   return chtml50->out;
2567 }
2568
2569
2570 /**
2571  * It is a handler who processes the H4 tag.
2572  *
2573  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2574  *                     destination is specified.
2575  * @param node   [i]   The H4 tag node is specified.
2576  * @return The conversion result is returned.
2577  */
2578 static char *
2579 s_chtml50_start_h4_tag(void *pdoc, Node *node)
2580 {
2581   chtml50_t   *chtml50;
2582   Doc         *doc;
2583   request_rec *r;
2584   Attr        *attr;
2585
2586   chtml50 = GET_CHTML50(pdoc);
2587   doc     = chtml50->doc;
2588   r       = doc->r;
2589
2590   W_L("<h4");
2591   for (attr = qs_get_attr(doc,node);
2592        attr;
2593        attr = qs_get_next_attr(doc,attr)) {
2594     char *name  = qs_get_attr_name(doc,attr);
2595     char *value = qs_get_attr_value(doc,attr);
2596     if (STRCASEEQ('a','A',"align", name)) {
2597       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
2598         W_L(" align=\"");
2599         W_V(value);
2600         W_L("\"");
2601         break;
2602       }
2603     }
2604   }
2605   W_L(">");
2606   return chtml50->out;
2607 }
2608
2609
2610 /**
2611  * It is a handler who processes the H4 tag.
2612  *
2613  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2614  *                     destination is specified.
2615  * @param node   [i]   The H4 tag node is specified.
2616  * @return The conversion result is returned.
2617  */
2618 static char *
2619 s_chtml50_end_h4_tag(void *pdoc, Node *UNUSED(child)) 
2620 {
2621   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2622   Doc       *doc     = chtml50->doc;
2623
2624   W_L("</h4>");
2625
2626   return chtml50->out;
2627 }
2628
2629
2630 /**
2631  * It is a handler who processes the H5 tag.
2632  *
2633  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2634  *                     destination is specified.
2635  * @param node   [i]   The H5 tag node is specified.
2636  * @return The conversion result is returned.
2637  */
2638 static char *
2639 s_chtml50_start_h5_tag(void *pdoc, Node *node)
2640 {
2641   chtml50_t   *chtml50;
2642   Doc         *doc;
2643   request_rec *r;
2644   Attr        *attr;
2645
2646   chtml50 = GET_CHTML50(pdoc);
2647   doc     = chtml50->doc;
2648   r       = doc->r;
2649
2650   W_L("<h5");
2651   for (attr = qs_get_attr(doc,node);
2652        attr;
2653        attr = qs_get_next_attr(doc,attr)) {
2654     char *name  = qs_get_attr_name(doc,attr);
2655     char *value = qs_get_attr_value(doc,attr);
2656     if (STRCASEEQ('a','A',"align", name)) {
2657       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
2658         W_L(" align=\"");
2659         W_V(value);
2660         W_L("\"");
2661         break;
2662       }
2663     }
2664   }
2665   W_L(">");
2666   return chtml50->out;
2667 }
2668
2669
2670 /**
2671  * It is a handler who processes the H5 tag.
2672  *
2673  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2674  *                     destination is specified.
2675  * @param node   [i]   The H5 tag node is specified.
2676  * @return The conversion result is returned.
2677  */
2678 static char *
2679 s_chtml50_end_h5_tag(void *pdoc, Node *UNUSED(child)) 
2680 {
2681   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2682   Doc       *doc     = chtml50->doc;
2683
2684   W_L("</h5>");
2685
2686   return chtml50->out;
2687 }
2688
2689
2690 /**
2691  * It is a handler who processes the H6 tag.
2692  *
2693  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2694  *                     destination is specified.
2695  * @param node   [i]   The H6 tag node is specified.
2696  * @return The conversion result is returned.
2697  */
2698 static char *
2699 s_chtml50_start_h6_tag(void *pdoc, Node *node)
2700 {
2701   chtml50_t   *chtml50;
2702   Doc         *doc;
2703   request_rec *r;
2704   Attr        *attr;
2705
2706   chtml50 = GET_CHTML50(pdoc);
2707   doc     = chtml50->doc;
2708   r       = doc->r;
2709
2710   W_L("<h6");
2711   for (attr = qs_get_attr(doc,node);
2712        attr;
2713        attr = qs_get_next_attr(doc,attr)) {
2714     char *name  = qs_get_attr_name(doc,attr);
2715     char *value = qs_get_attr_value(doc,attr);
2716     if (STRCASEEQ('a','A',"align", name)) {
2717       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value) || STRCASEEQ('c','C',"center",value))) {
2718         W_L(" align=\"");
2719         W_V(value);
2720         W_L("\"");
2721         break;
2722       }
2723     }
2724   }
2725   W_L(">");
2726   return chtml50->out;
2727 }
2728
2729
2730 /**
2731  * It is a handler who processes the H6 tag.
2732  *
2733  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2734  *                     destination is specified.
2735  * @param node   [i]   The H6 tag node is specified.
2736  * @return The conversion result is returned.
2737  */
2738 static char *
2739 s_chtml50_end_h6_tag(void *pdoc, Node *UNUSED(child)) 
2740 {
2741   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2742   Doc       *doc     = chtml50->doc;
2743
2744   W_L("</h6>");
2745
2746   return chtml50->out;
2747 }
2748
2749
2750 /**
2751  * It is a handler who processes the TEXTARE tag.
2752  *
2753  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2754  *                     destination is specified.
2755  * @param node   [i]   The TEXTAREA tag node is specified.
2756  * @return The conversion result is returned.
2757  */
2758 static char *
2759 s_chtml50_start_textarea_tag(void *pdoc, Node *node) 
2760 {
2761   chtml50_t     *chtml50;
2762   Doc           *doc;
2763   request_rec   *r;
2764   Attr          *attr;
2765
2766   chtml50 = GET_CHTML50(pdoc);
2767   doc     = chtml50->doc;
2768   r       = doc->r;
2769
2770   chtml50->textarea_flag++;
2771
2772   W_L("<textarea");
2773   for (attr = qs_get_attr(doc,node);
2774        attr;
2775        attr = qs_get_next_attr(doc,attr)) {
2776     char *name  = qs_get_attr_name(doc,attr);
2777     char *value = qs_get_attr_value(doc,attr);
2778     if (STRCASEEQ('a','A',"accesskey",name) && value && *value != 0) {
2779       W_L(" accesskey=\"");
2780       W_V(value);
2781       W_L("\"");
2782     }
2783     else if (STRCASEEQ('i','I',"istyle", name) && value && (*value == '1' || *value == '2' || *value == '3' || *value == '4')) {
2784       W_L(" istyle=\"");
2785       W_V(value);
2786       W_L("\"");
2787     }
2788     else if (STRCASEEQ('n','N',"name", name) && value && *value) {
2789       W_L(" name=\"");
2790       W_V(value);
2791       W_L("\"");
2792     }
2793     else if (STRCASEEQ('r','R',"rows", name) && value && *value) {
2794       W_L(" rows=\"");
2795       W_V(value);
2796       W_L("\"");
2797     }
2798     else if (STRCASEEQ('c','C',"cols", name) && value && *value) {
2799       W_L(" cols=\"");
2800       W_V(value);
2801       W_L("\"");
2802     }
2803   }
2804   W_L(">");
2805   return chtml50->out;
2806 }
2807
2808
2809 /**
2810  * It is a handler who processes the TEXTAREA tag.
2811  *
2812  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2813  *                     destination is specified.
2814  * @param node   [i]   The TEXTAREA tag node is specified.
2815  * @return The conversion result is returned.
2816  */
2817 static char *
2818 s_chtml50_end_textarea_tag(void *pdoc, Node *UNUSED(child)) 
2819 {
2820   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2821   Doc       *doc     = chtml50->doc;
2822
2823   W_L("</textarea>");
2824   chtml50->textarea_flag--;
2825
2826   return chtml50->out;
2827 }
2828
2829
2830 static char *
2831 s_chtml50_chxjif_tag(void *pdoc, Node *node)
2832 {
2833   Node        *child;
2834   chtml50_t   *chtml50;
2835   Doc         *doc;
2836   request_rec *r;
2837
2838   chtml50 = GET_CHTML50(pdoc);
2839   doc     = chtml50->doc;
2840   r       = doc->r;
2841
2842   for (child = qs_get_child_node(doc, node);
2843        child;
2844        child = qs_get_next_node(doc, child)) {
2845     W_V(child->otext);
2846     s_chtml50_chxjif_tag(chtml50, child);
2847   }
2848
2849   return NULL;
2850 }
2851
2852
2853 static char *
2854 s_chtml50_text_tag(void *pdoc, Node *child)
2855 {
2856   chtml50_t   *chtml50;
2857   Doc         *doc;
2858   request_rec *r;
2859
2860   char        *textval;
2861   char        *tmp;
2862   char        *tdst;
2863   char        one_byte[2];
2864   int         ii;
2865   int         tdst_len;
2866
2867   chtml50 = GET_CHTML50(pdoc);
2868   doc     = chtml50->doc;
2869   r       = doc->r;
2870   
2871   textval = qs_get_node_value(doc,child);
2872   if (strlen(textval) == 0) {
2873     return chtml50->out;
2874   }
2875   
2876   tmp = apr_palloc(r->pool, qs_get_node_size(doc,child)+1);
2877   memset(tmp, 0, qs_get_node_size(doc,child)+1);
2878   
2879   tdst     = qs_alloc_zero_byte_string(doc->buf.pool);
2880   memset(one_byte, 0, sizeof(one_byte));
2881   tdst_len = 0;
2882   
2883   for (ii=0; ii<qs_get_node_size(doc,child); ii++) {
2884     char* out;
2885     int rtn = s_chtml50_search_emoji(chtml50, &textval[ii], &out);
2886     if (rtn) {
2887       tdst = qs_out_apr_pstrcat(r, tdst, out, &tdst_len);
2888       ii+=(rtn - 1);
2889       continue;
2890     }
2891   
2892     if (is_sjis_kanji(textval[ii])) {
2893       one_byte[0] = textval[ii+0];
2894       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
2895       one_byte[0] = textval[ii+1];
2896       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
2897       ii++;
2898     }
2899     else if (chtml50->pre_flag) {
2900       one_byte[0] = textval[ii+0];
2901       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
2902     }
2903     else if (chtml50->textarea_flag) {
2904       one_byte[0] = textval[ii+0];
2905       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
2906     }
2907     else if (textval[ii] != '\r' && textval[ii] != '\n') {
2908       one_byte[0] = textval[ii+0];
2909       tdst = qs_out_apr_pstrcat(r, tdst, one_byte, &tdst_len);
2910     }
2911   }
2912   W_V(tdst);
2913   return chtml50->out;
2914 }
2915
2916
2917 /**
2918  * It is a handler who processes the BLOCKQUOTE tag.
2919  *
2920  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2921  *                     destination is specified.
2922  * @param node   [i]   The BLOCKQUOTE tag node is specified.
2923  * @return The conversion result is returned.
2924  */
2925 static char *
2926 s_chtml50_start_blockquote_tag(void *pdoc, Node *UNUSED(child))
2927 {
2928   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2929   Doc       *doc     = chtml50->doc;
2930   W_L("<blockquote>");
2931   return chtml50->out;
2932 }
2933
2934
2935 /**
2936  * It is a handler who processes the BLOCKQUOTE tag.
2937  *
2938  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2939  *                     destination is specified.
2940  * @param node   [i]   The BLOCKQUOTE tag node is specified.
2941  * @return The conversion result is returned.
2942  */
2943 static char *
2944 s_chtml50_end_blockquote_tag(void *pdoc, Node *UNUSED(child))
2945 {
2946   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2947   Doc       *doc     = chtml50->doc;
2948   W_L("</blockquote>");
2949   return chtml50->out;
2950 }
2951
2952
2953 /**
2954  * It is a handler who processes the DIR tag.
2955  *
2956  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2957  *                     destination is specified.
2958  * @param node   [i]   The DIR tag node is specified.
2959  * @return The conversion result is returned.
2960  */
2961 static char *
2962 s_chtml50_start_dir_tag(void *pdoc, Node *node)
2963 {
2964   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2965   Doc       *doc     = chtml50->doc;
2966   Attr      *attr;
2967   W_L("<dir");
2968   for (attr = qs_get_attr(doc,node);
2969        attr;
2970        attr = qs_get_next_attr(doc,attr)) {
2971     char *name   = qs_get_attr_name(doc,attr);
2972     char *value  = qs_get_attr_value(doc,attr);
2973     if (STRCASEEQ('t','T',"type",name)) {
2974       if (value && (STRCASEEQ('d','D',"disc",value) || STRCASEEQ('c','C',"circle",value) || STRCASEEQ('s','S',"square",value))) {
2975         W_L(" type=\"");
2976         W_V(value);
2977         W_L("\"");
2978       }
2979     }
2980   }
2981   W_L(">");
2982   return chtml50->out;
2983 }
2984
2985
2986 /**
2987  * It is a handler who processes the DIR tag.
2988  *
2989  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
2990  *                     destination is specified.
2991  * @param node   [i]   The DIR tag node is specified.
2992  * @return The conversion result is returned.
2993  */
2994 static char *
2995 s_chtml50_end_dir_tag(void *pdoc, Node *UNUSED(child))
2996 {
2997   chtml50_t *chtml50 = GET_CHTML50(pdoc);
2998   Doc       *doc = chtml50->doc;
2999   W_L("</dir>");
3000   return chtml50->out;
3001 }
3002
3003
3004 /**
3005  * It is a handler who processes the DL tag.
3006  *
3007  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3008  *                     destination is specified.
3009  * @param node   [i]   The DL tag node is specified.
3010  * @return The conversion result is returned.
3011  */
3012 static char *
3013 s_chtml50_start_dl_tag(void *pdoc, Node *UNUSED(child))
3014 {
3015   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3016   Doc       *doc     = chtml50->doc;
3017   W_L("<dl>");
3018   return chtml50->out;
3019 }
3020
3021
3022 /**
3023  * It is a handler who processes the DL tag.
3024  *
3025  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3026  *                     destination is specified.
3027  * @param node   [i]   The DL tag node is specified.
3028  * @return The conversion result is returned.
3029  */
3030 static char *
3031 s_chtml50_end_dl_tag(void *pdoc, Node *UNUSED(child))
3032 {
3033   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3034   Doc       *doc     = chtml50->doc;
3035   W_L("</dl>");
3036   return chtml50->out;
3037 }
3038
3039
3040 /**
3041  * It is a handler who processes the DT tag.
3042  *
3043  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3044  *                     destination is specified.
3045  * @param node   [i]   The DT tag node is specified.
3046  * @return The conversion result is returned.
3047  */
3048 static char *
3049 s_chtml50_start_dt_tag(void *pdoc, Node *UNUSED(child))
3050 {
3051   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3052   Doc       *doc     = chtml50->doc;
3053   W_L("<dt>");
3054   return chtml50->out;
3055 }
3056
3057
3058 /**
3059  * It is a handler who processes the DT tag.
3060  *
3061  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3062  *                     destination is specified.
3063  * @param node   [i]   The DT tag node is specified.
3064  * @return The conversion result is returned.
3065  */
3066 static char *
3067 s_chtml50_end_dt_tag(void *pdoc, Node *UNUSED(child))
3068 {
3069   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3070
3071   return chtml50->out;
3072 }
3073
3074
3075 /**
3076  * It is a handler who processes the DD tag.
3077  *
3078  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3079  *                     destination is specified.
3080  * @param node   [i]   The DD tag node is specified.
3081  * @return The conversion result is returned.
3082  */
3083 static char *
3084 s_chtml50_start_dd_tag(void *pdoc, Node *UNUSED(child))
3085 {
3086   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3087   Doc       *doc     = chtml50->doc;
3088
3089   W_L("<dd>");
3090
3091   return chtml50->out;
3092 }
3093
3094
3095 /**
3096  * It is a handler who processes the DD tag.
3097  *
3098  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3099  *                     destination is specified.
3100  * @param node   [i]   The DD tag node is specified.
3101  * @return The conversion result is returned.
3102  */
3103 static char *
3104 s_chtml50_end_dd_tag(void *pdoc, Node *UNUSED(child))
3105 {
3106   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3107
3108   return chtml50->out;
3109 }
3110
3111
3112 /**
3113  * It is a handler who processes the MARQUEE tag.
3114  *
3115  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3116  *                     destination is specified.
3117  * @param node   [i]   The MARQUEE tag node is specified.
3118  * @return The conversion result is returned.
3119  */
3120 static char *
3121 s_chtml50_start_marquee_tag(void *pdoc, Node *node)
3122 {
3123   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3124   Doc       *doc = chtml50->doc;
3125   Attr      *attr;
3126   W_L("<marquee");
3127   /*--------------------------------------------------------------------------*/
3128   /* Get Attributes                                                           */
3129   /*--------------------------------------------------------------------------*/
3130   for (attr = qs_get_attr(doc,node);
3131        attr;
3132        attr = qs_get_next_attr(doc,attr)) {
3133     char *name   = qs_get_attr_name(doc,attr);
3134     char *value  = qs_get_attr_value(doc,attr);
3135     if (STRCASEEQ('d','D',"direction", name)) {
3136       if (value && (STRCASEEQ('l','L',"left",value) || STRCASEEQ('r','R',"right",value))) {
3137         W_L(" direction=\"");
3138         W_V(value);
3139         W_L("\"");
3140       }
3141     }
3142     else if (STRCASEEQ('b','B',"behavior",name)) {
3143       if (value && (STRCASEEQ('s','S',"scroll",value) || STRCASEEQ('s','S',"slide",value) || STRCASEEQ('a','A',"alternate",value))) {
3144         W_L(" behavior=\""); 
3145         W_V(value);
3146         W_L("\"");
3147       }
3148     }
3149     else if (STRCASEEQ('l','L',"loop",name)) {
3150       if (value && *value) {
3151         W_L(" loop=\"");
3152         W_V(value);
3153         W_L("\"");
3154       }
3155     }
3156     else if (STRCASEEQ('b','B',"bgcolor",name)) {
3157       if (value && *value) {
3158         W_L(" bgcolor=\"");
3159         W_V(value);
3160         W_L("\"");
3161       }
3162     }
3163   }
3164   W_L(">");
3165   return chtml50->out;
3166 }
3167
3168
3169 /**
3170  * It is a handler who processes the MARQUEE tag.
3171  *
3172  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3173  *                     destination is specified.
3174  * @param node   [i]   The MARQUEE tag node is specified.
3175  * @return The conversion result is returned.
3176  */
3177 static char *
3178 s_chtml50_end_marquee_tag(void *pdoc, Node *UNUSED(child))
3179 {
3180   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3181   Doc       *doc = chtml50->doc;
3182   W_L("</marquee>");
3183   return chtml50->out;
3184 }
3185
3186
3187 /**
3188  * It is a handler who processes the BLINK tag.
3189  *
3190  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3191  *                     destination is specified.
3192  * @param node   [i]   The BLINK tag node is specified.
3193  * @return The conversion result is returned.
3194  */
3195 static char *
3196 s_chtml50_start_blink_tag(void *pdoc, Node *UNUSED(child))
3197 {
3198   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3199   Doc       *doc = chtml50->doc;
3200   W_L("<blink>");
3201   return chtml50->out;
3202 }
3203
3204
3205 /**
3206  * It is a handler who processes the BLINK tag.
3207  *
3208  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3209  *                     destination is specified.
3210  * @param node   [i]   The BLINK tag node is specified.
3211  * @return The conversion result is returned.
3212  */
3213 static char *
3214 s_chtml50_end_blink_tag(void *pdoc, Node *UNUSED(child))
3215 {
3216   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3217   Doc       *doc = chtml50->doc;
3218   W_L("</blink>");
3219   return chtml50->out;
3220 }
3221
3222
3223 /**
3224  * It is a handler who processes the MENU tag.
3225  *
3226  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3227  *                     destination is specified.
3228  * @param node   [i]   The MENU tag node is specified.
3229  * @return The conversion result is returned.
3230  */
3231 static char *
3232 s_chtml50_start_menu_tag(void *pdoc, Node *node)
3233 {
3234   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3235   Doc       *doc     = chtml50->doc;
3236   Attr      *attr;
3237   W_L("<menu");
3238   /*--------------------------------------------------------------------------*/
3239   /* Get Attributes                                                           */
3240   /*--------------------------------------------------------------------------*/
3241   for (attr = qs_get_attr(doc,node);
3242        attr;
3243        attr = qs_get_next_attr(doc,attr)) {
3244     char *name   = qs_get_attr_name(doc,attr);
3245     char *value  = qs_get_attr_value(doc,attr);
3246     if (STRCASEEQ('t','T',"type",name)) {
3247       if (value && (STRCASEEQ('d','D',"disc",value) || STRCASEEQ('c','C',"circle",value) || STRCASEEQ('s','S',"square",value))) {
3248         W_L(" type=\"");
3249         W_V(value);
3250         W_L("\"");
3251       }
3252     }
3253   }
3254   W_L(">");
3255   return chtml50->out;
3256 }
3257
3258
3259 /**
3260  * It is a handler who processes the MENU tag.
3261  *
3262  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3263  *                     destination is specified.
3264  * @param node   [i]   The MENU tag node is specified.
3265  * @return The conversion result is returned.
3266  */
3267 static char *
3268 s_chtml50_end_menu_tag(void *pdoc, Node *UNUSED(child))
3269 {
3270   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3271   Doc       *doc = chtml50->doc;
3272   W_L("</menu>");
3273   return chtml50->out;
3274 }
3275
3276
3277 /**
3278  * It is a handler who processes the PLAINTEXT tag.
3279  *
3280  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3281  *                     destination is specified.
3282  * @param node   [i]   The PLAINTEXT tag node is specified.
3283  * @return The conversion result is returned.
3284  */
3285 static char *
3286 s_chtml50_start_plaintext_tag(void *pdoc, Node *node)
3287 {
3288   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3289   Doc       *doc     = chtml50->doc;
3290   W_L("<plaintext>");
3291   s_chtml50_start_plaintext_tag_inner(pdoc,node);
3292   return chtml50->out;
3293 }
3294
3295 static char *
3296 s_chtml50_start_plaintext_tag_inner(void *pdoc, Node *node)
3297 {
3298   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3299   Doc       *doc     = chtml50->doc;
3300   Node      *child;
3301   for (child = qs_get_child_node(doc, node);
3302        child;
3303        child = qs_get_next_node(doc, child)) {
3304     W_V(child->otext);
3305     s_chtml50_start_plaintext_tag_inner(pdoc, child);
3306   }
3307   return chtml50->out;
3308 }
3309
3310
3311 /**
3312  * It is a handler who processes the PLAINTEXT tag.
3313  *
3314  * @param pdoc  [i/o] The pointer to the CHTML structure at the output
3315  *                     destination is specified.
3316  * @param node   [i]   The PLAINTEXT tag node is specified.
3317  * @return The conversion result is returned.
3318  */
3319 static char *
3320 s_chtml50_end_plaintext_tag(void *pdoc, Node *UNUSED(child))
3321 {
3322   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3323   return chtml50->out;
3324 }
3325
3326
3327 /**
3328  * It is handler who processes the New Line Code.
3329  */
3330 static char *
3331 s_chtml50_newline_mark(void *pdoc, Node *UNUSED(node))
3332 {
3333   chtml50_t *chtml50 = GET_CHTML50(pdoc);
3334   Doc *doc = chtml50->doc;
3335   W_NLCODE();
3336   return chtml50->out;
3337 }
3338 /*
3339  * vim:ts=2 et
3340  */