[BACK]Return to html.c CVS log [TXT][DIR] Up to [cvsweb.bsd.lv] / mandoc

Annotation of mandoc/html.c, Revision 1.4

1.4     ! kristaps    1: /* $Id: html.c,v 1.3 2008/12/03 21:27:56 kristaps Exp $ */
1.1       kristaps    2: /*
                      3:  * Copyright (c) 2008 Kristaps Dzonsons <kristaps@kth.se>
                      4:  *
                      5:  * Permission to use, copy, modify, and distribute this software for any
                      6:  * purpose with or without fee is hereby granted, provided that the
                      7:  * above copyright notice and this permission notice appear in all
                      8:  * copies.
                      9:  *
                     10:  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
                     11:  * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
                     12:  * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
                     13:  * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
                     14:  * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
                     15:  * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
                     16:  * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
                     17:  * PERFORMANCE OF THIS SOFTWARE.
                     18:  */
1.4     ! kristaps   19: #include <sys/param.h>
        !            20: #include <sys/stat.h>
        !            21:
1.1       kristaps   22: #include <assert.h>
1.4     ! kristaps   23: #include <err.h>
        !            24: #include <fcntl.h>
1.1       kristaps   25: #include <stdlib.h>
1.4     ! kristaps   26: #include <stdio.h>
1.2       kristaps   27: #include <string.h>
1.4     ! kristaps   28: #include <unistd.h>
1.1       kristaps   29:
                     30: #include "libmdocml.h"
                     31: #include "private.h"
1.2       kristaps   32: #include "ml.h"
                     33:
                     34:
1.4     ! kristaps   35: static int             html_loadcss(struct md_mbuf *, const char *);
        !            36:
1.2       kristaps   37: static ssize_t         html_endtag(struct md_mbuf *,
                     38:                                const struct md_args *,
                     39:                                enum md_ns, int);
                     40: static ssize_t         html_begintag(struct md_mbuf *,
                     41:                                const struct md_args *,
                     42:                                enum md_ns, int,
                     43:                                const int *, const char **);
1.4     ! kristaps   44: static int             html_begin(struct md_mbuf *,
        !            45:                                const struct md_args *,
        !            46:                                const struct tm *,
        !            47:                                const char *, const char *,
        !            48:                                const char *, const char *);
1.2       kristaps   49: static int             html_end(struct md_mbuf *,
                     50:                                const struct md_args *);
                     51: static ssize_t         html_blocktagname(struct md_mbuf *,
                     52:                                const struct md_args *, int);
                     53: static ssize_t         html_blocktagargs(struct md_mbuf *,
                     54:                                const struct md_args *, int,
                     55:                                const int *, const char **);
1.3       kristaps   56: static ssize_t         html_blockheadtagname(struct md_mbuf *,
                     57:                                const struct md_args *, int);
                     58: static ssize_t         html_blockheadtagargs(struct md_mbuf *,
                     59:                                const struct md_args *, int,
                     60:                                const int *, const char **);
                     61: static ssize_t         html_blockbodytagname(struct md_mbuf *,
                     62:                                const struct md_args *, int);
                     63: static ssize_t         html_blockbodytagargs(struct md_mbuf *,
                     64:                                const struct md_args *, int,
                     65:                                const int *, const char **);
1.2       kristaps   66: static ssize_t         html_inlinetagname(struct md_mbuf *,
                     67:                                const struct md_args *, int);
                     68: static ssize_t         html_inlinetagargs(struct md_mbuf *,
                     69:                                const struct md_args *, int,
                     70:                                const int *, const char **);
                     71:
                     72:
1.4     ! kristaps   73: static int
        !            74: html_loadcss(struct md_mbuf *mbuf, const char *css)
        !            75: {
        !            76:        size_t           res, bufsz;
        !            77:        char            *buf;
        !            78:        struct stat      st;
        !            79:        int              fd, c;
        !            80:        ssize_t          ssz;
        !            81:
        !            82:        c = 0;
        !            83:        res = 0;
        !            84:        buf = NULL;
        !            85:
        !            86:        if (-1 == (fd = open(css, O_RDONLY, 0))) {
        !            87:                warn("%s", css);
        !            88:                return(0);
        !            89:        }
        !            90:
        !            91:        if (-1 == fstat(fd, &st)) {
        !            92:                warn("%s", css);
        !            93:                goto out;
        !            94:        }
        !            95:
        !            96:        bufsz = MAX(st.st_blksize, BUFSIZ);
        !            97:        if (NULL == (buf = malloc(bufsz))) {
        !            98:                warn("malloc");
        !            99:                goto out;
        !           100:        }
        !           101:
        !           102:        for (;;) {
        !           103:                if (-1 == (ssz = read(fd, buf, bufsz))) {
        !           104:                        warn("%s", css);
        !           105:                        goto out;
        !           106:                } else if (0 == ssz)
        !           107:                        break;
        !           108:                if ( ! ml_nputs(mbuf, buf, (size_t)ssz, &res))
        !           109:                        goto out;
        !           110:        }
        !           111:
        !           112:        c = 1;
        !           113:
        !           114: out:
        !           115:        if (-1 == close(fd)) {
        !           116:                warn("%s", css);
        !           117:                c = 0;
        !           118:        }
        !           119:
        !           120:        if (buf)
        !           121:                free(buf);
        !           122:
        !           123:        return(c);
        !           124: }
        !           125:
        !           126:
1.3       kristaps  127: /* ARGSUSED */
1.2       kristaps  128: static int
1.4     ! kristaps  129: html_begin(struct md_mbuf *mbuf, const struct md_args *args,
        !           130:                const struct tm *tm, const char *os,
        !           131:                const char *title, const char *section,
        !           132:                const char *vol)
1.2       kristaps  133: {
1.4     ! kristaps  134:        const char      *preamble, *css, *trail;
        !           135:        char             buf[512];
1.2       kristaps  136:        size_t           res;
                    137:
1.4     ! kristaps  138:        preamble =
        !           139:        "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01//EN\"\n"
        !           140:        "    \"http://www.w3.org/TR/html4/strict.dtd\">\n"
        !           141:        "<html>\n"
        !           142:        "<head>\n"
        !           143:        "    <meta http-equiv=\"Content-Type\"\n"
        !           144:        "         content=\"text/html;charset=utf-8\">\n"
        !           145:        "    <meta name=\"resource-type\" content=\"document\">\n"
        !           146:        "    <title>Manual Page for %s(%s)</title>\n";
        !           147:
        !           148:        css =
        !           149:        "    <link rel=\"stylesheet\" type=\"text/css\"\n"
        !           150:        "         href=\"%s\">\n";
        !           151:        trail =
        !           152:        "</head>\n"
        !           153:        "<body>\n"
        !           154:        "<div class=\"mdoc\">\n";
        !           155:
1.2       kristaps  156:        res = 0;
1.4     ! kristaps  157:
        !           158:        (void)snprintf(buf, sizeof(buf) - 1,
        !           159:                        preamble, title, section);
        !           160:
        !           161:        if ( ! ml_puts(mbuf, buf, &res))
1.2       kristaps  162:                return(0);
1.4     ! kristaps  163:
        !           164:        assert(args->params.html.css);
        !           165:        if (HTML_CSS_EMBED & args->params.html.flags) {
        !           166:                if ( ! ml_puts(mbuf, "    <style><!--\n", &res))
        !           167:                        return(0);
        !           168:                if ( ! html_loadcss(mbuf, args->params.html.css))
        !           169:                        return(0);
        !           170:                if ( ! ml_puts(mbuf, "    --!></style>\n", &res))
        !           171:                        return(0);
        !           172:        } else {
        !           173:                (void)snprintf(buf, sizeof(buf) - 1, css,
        !           174:                                args->params.html.css);
        !           175:                if ( ! ml_puts(mbuf, buf, &res))
        !           176:                        return(0);
        !           177:        }
        !           178:
        !           179:        if ( ! ml_puts(mbuf, trail, &res))
1.2       kristaps  180:                return(0);
                    181:
                    182:        return(1);
                    183: }
                    184:
                    185:
1.3       kristaps  186: /* ARGSUSED */
1.2       kristaps  187: static int
                    188: html_end(struct md_mbuf *mbuf, const struct md_args *args)
                    189: {
                    190:        size_t           res;
                    191:
                    192:        res = 0;
1.4     ! kristaps  193:        if ( ! ml_puts(mbuf, "</div></body>\n</html>", &res))
1.2       kristaps  194:                return(0);
                    195:
                    196:        return(1);
                    197: }
                    198:
                    199:
1.3       kristaps  200: /* ARGSUSED */
1.2       kristaps  201: static ssize_t
1.3       kristaps  202: html_blockbodytagname(struct md_mbuf *mbuf,
1.2       kristaps  203:                const struct md_args *args, int tok)
                    204: {
                    205:        size_t           res;
                    206:
                    207:        res = 0;
1.4     ! kristaps  208:        if ( ! ml_puts(mbuf, "div", &res))
        !           209:                return(-1);
1.3       kristaps  210:
                    211:        return((ssize_t)res);
                    212: }
                    213:
                    214:
                    215:
                    216:
                    217: /* ARGSUSED */
                    218: static ssize_t
                    219: html_blockheadtagname(struct md_mbuf *mbuf,
                    220:                const struct md_args *args, int tok)
                    221: {
                    222:        size_t           res;
                    223:
                    224:        res = 0;
1.4     ! kristaps  225:        if ( ! ml_puts(mbuf, "div", &res))
        !           226:                return(-1);
1.3       kristaps  227:
                    228:        return((ssize_t)res);
                    229: }
                    230:
                    231:
                    232: /* ARGSUSED */
                    233: static ssize_t
                    234: html_blocktagname(struct md_mbuf *mbuf,
                    235:                const struct md_args *args, int tok)
                    236: {
                    237:        size_t           res;
                    238:
                    239:        res = 0;
1.4     ! kristaps  240:        if ( ! ml_puts(mbuf, "div", &res))
        !           241:                return(-1);
1.2       kristaps  242:
1.3       kristaps  243:        return((ssize_t)res);
                    244: }
                    245:
                    246:
                    247: /* ARGSUSED */
                    248: static ssize_t
                    249: html_blockheadtagargs(struct md_mbuf *mbuf, const struct md_args *args,
                    250:                int tok, const int *argc, const char **argv)
                    251: {
                    252:        size_t           res;
                    253:
                    254:        res = 0;
                    255:
1.4     ! kristaps  256:        if ( ! ml_puts(mbuf, " class=\"head-", &res))
1.3       kristaps  257:                return(0);
                    258:        if ( ! ml_puts(mbuf, toknames[tok], &res))
                    259:                return(0);
                    260:        if ( ! ml_puts(mbuf, "\"", &res))
                    261:                return(0);
                    262:
                    263:        switch (tok) {
                    264:        default:
                    265:                break;
                    266:        }
                    267:
                    268:        return(0);
                    269: }
                    270:
                    271:
                    272: /* ARGSUSED */
                    273: static ssize_t
                    274: html_blockbodytagargs(struct md_mbuf *mbuf, const struct md_args *args,
                    275:                int tok, const int *argc, const char **argv)
                    276: {
                    277:        size_t           res;
                    278:
                    279:        res = 0;
                    280:
1.4     ! kristaps  281:        if ( ! ml_puts(mbuf, " class=\"body-", &res))
1.3       kristaps  282:                return(0);
                    283:        if ( ! ml_puts(mbuf, toknames[tok], &res))
                    284:                return(0);
                    285:        if ( ! ml_puts(mbuf, "\"", &res))
                    286:                return(0);
                    287:
                    288:        switch (tok) {
                    289:        default:
                    290:                break;
                    291:        }
                    292:
                    293:        return(res);
1.2       kristaps  294: }
                    295:
                    296:
                    297: /* ARGSUSED */
                    298: static ssize_t
                    299: html_blocktagargs(struct md_mbuf *mbuf, const struct md_args *args,
                    300:                int tok, const int *argc, const char **argv)
                    301: {
1.3       kristaps  302:        size_t           res;
                    303:
                    304:        res = 0;
                    305:
1.4     ! kristaps  306:        if ( ! ml_puts(mbuf, " class=\"block-", &res))
1.3       kristaps  307:                return(0);
                    308:        if ( ! ml_puts(mbuf, toknames[tok], &res))
                    309:                return(0);
                    310:        if ( ! ml_puts(mbuf, "\"", &res))
                    311:                return(0);
1.2       kristaps  312:
                    313:        switch (tok) {
                    314:        default:
1.3       kristaps  315:                break;
1.2       kristaps  316:        }
                    317:
1.3       kristaps  318:        return(0);
1.2       kristaps  319: }
1.1       kristaps  320:
                    321:
                    322: /* ARGSUSED */
1.2       kristaps  323: static ssize_t
                    324: html_inlinetagargs(struct md_mbuf *mbuf, const struct md_args *args,
                    325:                int tok, const int *argc, const char **argv)
                    326: {
1.3       kristaps  327:        size_t           res;
                    328:
                    329:        res = 0;
                    330:
1.4     ! kristaps  331:        if ( ! ml_puts(mbuf, " class=\"inline-", &res))
1.3       kristaps  332:                return(0);
                    333:        if ( ! ml_puts(mbuf, toknames[tok], &res))
                    334:                return(0);
                    335:        if ( ! ml_puts(mbuf, "\"", &res))
                    336:                return(0);
                    337:
1.2       kristaps  338:
                    339:        switch (tok) {
                    340:        default:
1.3       kristaps  341:                break;
1.2       kristaps  342:        }
                    343:
1.3       kristaps  344:        return(0);
1.2       kristaps  345: }
                    346:
                    347:
1.3       kristaps  348: /* ARGSUSED */
1.2       kristaps  349: static ssize_t
                    350: html_inlinetagname(struct md_mbuf *mbuf,
                    351:                const struct md_args *args, int tok)
                    352: {
                    353:        size_t           res;
                    354:
                    355:        res = 0;
                    356:
                    357:        switch (tok) {
1.4     ! kristaps  358:        case (ROFF_Pp):
        !           359:                if ( ! ml_puts(mbuf, "div", &res))
        !           360:                        return(-1);
        !           361:                break;
1.2       kristaps  362:        default:
                    363:                if ( ! ml_puts(mbuf, "span", &res))
                    364:                        return(-1);
                    365:                break;
                    366:        }
                    367:
                    368:        return((ssize_t)res);
                    369: }
                    370:
                    371:
                    372: static ssize_t
                    373: html_begintag(struct md_mbuf *mbuf, const struct md_args *args,
                    374:                enum md_ns ns, int tok,
                    375:                const int *argc, const char **argv)
                    376: {
                    377:
                    378:        assert(ns != MD_NS_DEFAULT);
1.3       kristaps  379:        switch (ns) {
                    380:        case (MD_NS_BLOCK):
1.2       kristaps  381:                if ( ! html_blocktagname(mbuf, args, tok))
                    382:                        return(0);
                    383:                return(html_blocktagargs(mbuf, args,
                    384:                                        tok, argc, argv));
1.3       kristaps  385:        case (MD_NS_BODY):
                    386:                if ( ! html_blockbodytagname(mbuf, args, tok))
                    387:                        return(0);
                    388:                return(html_blockbodytagargs(mbuf, args,
                    389:                                        tok, argc, argv));
                    390:        case (MD_NS_HEAD):
                    391:                if ( ! html_blockheadtagname(mbuf, args, tok))
                    392:                        return(0);
                    393:                return(html_blockheadtagargs(mbuf, args,
                    394:                                        tok, argc, argv));
                    395:        default:
                    396:                break;
1.2       kristaps  397:        }
                    398:
                    399:        if ( ! html_inlinetagname(mbuf, args, tok))
                    400:                return(0);
                    401:        return(html_inlinetagargs(mbuf, args, tok, argc, argv));
                    402: }
                    403:
                    404:
                    405: static ssize_t
                    406: html_endtag(struct md_mbuf *mbuf, const struct md_args *args,
                    407:                enum md_ns ns, int tok)
                    408: {
                    409:
                    410:        assert(ns != MD_NS_DEFAULT);
1.3       kristaps  411:        switch (ns) {
                    412:        case (MD_NS_BLOCK):
1.2       kristaps  413:                return(html_blocktagname(mbuf, args, tok));
1.3       kristaps  414:        case (MD_NS_BODY):
                    415:                return(html_blockbodytagname(mbuf, args, tok));
                    416:        case (MD_NS_HEAD):
                    417:                return(html_blockheadtagname(mbuf, args, tok));
                    418:        default:
                    419:                break;
                    420:        }
1.2       kristaps  421:
                    422:        return(html_inlinetagname(mbuf, args, tok));
                    423: }
                    424:
                    425:
1.1       kristaps  426: int
                    427: md_line_html(void *data, char *buf)
                    428: {
                    429:
1.2       kristaps  430:        return(mlg_line((struct md_mlg *)data, buf));
1.1       kristaps  431: }
                    432:
                    433:
                    434: int
                    435: md_exit_html(void *data, int flush)
                    436: {
                    437:
1.2       kristaps  438:        return(mlg_exit((struct md_mlg *)data, flush));
1.1       kristaps  439: }
                    440:
                    441:
                    442: void *
                    443: md_init_html(const struct md_args *args,
                    444:                struct md_mbuf *mbuf, const struct md_rbuf *rbuf)
                    445: {
                    446:
1.2       kristaps  447:        return(mlg_alloc(args, rbuf, mbuf, html_begintag,
                    448:                                html_endtag, html_begin, html_end));
1.1       kristaps  449: }
1.2       kristaps  450:

CVSweb