=================================================================== RCS file: /cvs/mandoc/mdoc.c,v retrieving revision 1.101 retrieving revision 1.113 diff -u -p -r1.101 -r1.113 --- mandoc/mdoc.c 2009/08/19 11:58:32 1.101 +++ mandoc/mdoc.c 2009/10/30 05:58:38 1.113 @@ -1,4 +1,4 @@ -/* $Id: mdoc.c,v 1.101 2009/08/19 11:58:32 kristaps Exp $ */ +/* $Id: mdoc.c,v 1.113 2009/10/30 05:58:38 kristaps Exp $ */ /* * Copyright (c) 2008, 2009 Kristaps Dzonsons * @@ -14,6 +14,8 @@ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ +#include + #include #include #include @@ -22,12 +24,12 @@ #include #include "libmdoc.h" +#include "libmandoc.h" const char *const __mdoc_merrnames[MERRMAX] = { "trailing whitespace", /* ETAILWS */ "unexpected quoted parameter", /* EQUOTPARM */ "unterminated quoted parameter", /* EQUOTTERM */ - "system: malloc error", /* EMALLOC */ "argument parameter suggested", /* EARGVAL */ "macro disallowed in prologue", /* EBODYPROL */ "macro disallowed in body", /* EPROLBODY */ @@ -74,7 +76,9 @@ const char *const __mdoc_merrnames[MERRMAX] = { "unclosed explicit scope", /* EOPEN */ "unterminated quoted phrase", /* EQUOTPHR */ "closure macro without prior context", /* ENOCTX */ - "no description found for library" /* ELIB */ + "no description found for library", /* ELIB */ + "bad child for parent context", /* EBADCHILD */ + "list arguments preceding type", /* ENOTYPE */ }; const char *const __mdoc_macronames[MDOC_MAX] = { @@ -112,7 +116,9 @@ const char *const __mdoc_macronames[MDOC_MAX] = { /* LINTED */ "Brc", "\%C", "Es", "En", /* LINTED */ - "Dx", "\%Q", "br", "sp" + "Dx", "\%Q", "br", "sp", + /* LINTED */ + "\%U" }; const char *const __mdoc_argnames[MDOC_ARG_MAX] = { @@ -124,14 +130,14 @@ const char *const __mdoc_argnames[MDOC_ARG_MAX] = { "ohang", "inset", "column", "width", "compact", "std", "filled", "words", "emphasis", - "symbolic", "nested" + "symbolic", "nested", "centered" }; const char * const *mdoc_macronames = __mdoc_macronames; const char * const *mdoc_argnames = __mdoc_argnames; static void mdoc_free1(struct mdoc *); -static int mdoc_alloc1(struct mdoc *); +static void mdoc_alloc1(struct mdoc *); static struct mdoc_node *node_alloc(struct mdoc *, int, int, int, enum mdoc_type); static int node_append(struct mdoc *, @@ -188,21 +194,17 @@ mdoc_free1(struct mdoc *mdoc) /* * Allocate all volatile resources (parse tree, meta-data, fields). */ -static int +static void mdoc_alloc1(struct mdoc *mdoc) { - bzero(&mdoc->meta, sizeof(struct mdoc_meta)); + memset(&mdoc->meta, 0, sizeof(struct mdoc_meta)); mdoc->flags = 0; mdoc->lastnamed = mdoc->lastsec = SEC_NONE; - mdoc->last = calloc(1, sizeof(struct mdoc_node)); - if (NULL == mdoc->last) - return(0); - + mdoc->last = mandoc_calloc(1, sizeof(struct mdoc_node)); mdoc->first = mdoc->last; mdoc->last->type = MDOC_ROOT; mdoc->next = MDOC_NEXT_CHILD; - return(1); } @@ -212,12 +214,12 @@ mdoc_alloc1(struct mdoc *mdoc) * and the parser is ready for re-invocation on a new tree; however, * cross-parse non-volatile data is kept intact. */ -int +void mdoc_reset(struct mdoc *mdoc) { mdoc_free1(mdoc); - return(mdoc_alloc1(mdoc)); + mdoc_alloc1(mdoc); } @@ -230,8 +232,6 @@ mdoc_free(struct mdoc *mdoc) { mdoc_free1(mdoc); - if (mdoc->htab) - mdoc_hash_free(mdoc->htab); free(mdoc); } @@ -244,22 +244,17 @@ mdoc_alloc(void *data, int pflags, const struct mdoc_c { struct mdoc *p; - if (NULL == (p = calloc(1, sizeof(struct mdoc)))) - return(NULL); + p = mandoc_calloc(1, sizeof(struct mdoc)); + if (cb) - (void)memcpy(&p->cb, cb, sizeof(struct mdoc_cb)); + memcpy(&p->cb, cb, sizeof(struct mdoc_cb)); p->data = data; p->pflags = pflags; - if (NULL == (p->htab = mdoc_hash_alloc())) { - free(p); - return(NULL); - } else if (mdoc_alloc1(p)) - return(p); - - free(p); - return(NULL); + mdoc_hash_init(); + mdoc_alloc1(p); + return(p); } @@ -435,11 +430,7 @@ node_alloc(struct mdoc *m, int line, { struct mdoc_node *p; - if (NULL == (p = calloc(1, sizeof(struct mdoc_node)))) { - (void)mdoc_nerr(m, m->last, EMALLOC); - return(NULL); - } - + p = mandoc_calloc(1, sizeof(struct mdoc_node)); p->sec = m->lastsec; p->line = line; p->pos = pos; @@ -457,9 +448,10 @@ mdoc_tail_alloc(struct mdoc *m, int line, int pos, int struct mdoc_node *p; p = node_alloc(m, line, pos, tok, MDOC_TAIL); - if (NULL == p) + if ( ! node_append(m, p)) return(0); - return(node_append(m, p)); + m->next = MDOC_NEXT_CHILD; + return(1); } @@ -472,9 +464,10 @@ mdoc_head_alloc(struct mdoc *m, int line, int pos, int assert(m->last); p = node_alloc(m, line, pos, tok, MDOC_HEAD); - if (NULL == p) + if ( ! node_append(m, p)) return(0); - return(node_append(m, p)); + m->next = MDOC_NEXT_CHILD; + return(1); } @@ -484,9 +477,10 @@ mdoc_body_alloc(struct mdoc *m, int line, int pos, int struct mdoc_node *p; p = node_alloc(m, line, pos, tok, MDOC_BODY); - if (NULL == p) + if ( ! node_append(m, p)) return(0); - return(node_append(m, p)); + m->next = MDOC_NEXT_CHILD; + return(1); } @@ -497,12 +491,13 @@ mdoc_block_alloc(struct mdoc *m, int line, int pos, struct mdoc_node *p; p = node_alloc(m, line, pos, tok, MDOC_BLOCK); - if (NULL == p) - return(0); p->args = args; if (p->args) (args->refcnt)++; - return(node_append(m, p)); + if ( ! node_append(m, p)) + return(0); + m->next = MDOC_NEXT_CHILD; + return(1); } @@ -513,12 +508,13 @@ mdoc_elem_alloc(struct mdoc *m, int line, int pos, struct mdoc_node *p; p = node_alloc(m, line, pos, tok, MDOC_ELEM); - if (NULL == p) - return(0); p->args = args; if (p->args) (args->refcnt)++; - return(node_append(m, p)); + if ( ! node_append(m, p)) + return(0); + m->next = MDOC_NEXT_CHILD; + return(1); } @@ -529,15 +525,7 @@ pstring(struct mdoc *m, int line, int pos, const char size_t sv; n = node_alloc(m, line, pos, -1, MDOC_TEXT); - if (NULL == n) - return(mdoc_nerr(m, m->last, EMALLOC)); - - n->string = malloc(len + 1); - if (NULL == n->string) { - free(n); - return(mdoc_nerr(m, m->last, EMALLOC)); - } - + n->string = mandoc_malloc(len + 1); sv = strlcpy(n->string, p, len + 1); /* Prohibit truncation. */ @@ -647,7 +635,6 @@ parsetext(struct mdoc *m, int line, char *buf) - static int macrowarn(struct mdoc *m, int ln, const char *buf) { @@ -667,7 +654,7 @@ macrowarn(struct mdoc *m, int ln, const char *buf) int parsemacro(struct mdoc *m, int ln, char *buf) { - int i, j, c, ppos; + int i, j, c; char mac[5]; /* Empty lines are ignored. */ @@ -687,8 +674,6 @@ parsemacro(struct mdoc *m, int ln, char *buf) return(1); } - ppos = i; - /* Copy the first word into a nil-terminated buffer. */ for (j = 0; j < 4; j++, i++) { @@ -696,6 +681,12 @@ parsemacro(struct mdoc *m, int ln, char *buf) break; else if (' ' == buf[i]) break; + + /* Check for invalid characters. */ + + if (isgraph((u_char)buf[i])) + continue; + return(mdoc_perr(m, ln, i, EPRINT)); } mac[j] = 0; @@ -706,7 +697,7 @@ parsemacro(struct mdoc *m, int ln, char *buf) return(1); } - if (MDOC_MAX == (c = mdoc_hash_find(m->htab, mac))) { + if (MDOC_MAX == (c = mdoc_hash_find(mac))) { if ( ! macrowarn(m, ln, mac)) goto err; return(1); @@ -721,7 +712,7 @@ parsemacro(struct mdoc *m, int ln, char *buf) * Begin recursive parse sequence. Since we're at the start of * the line, we don't need to do callable/parseable checks. */ - if ( ! mdoc_macro(m, c, ln, ppos, &i, buf)) + if ( ! mdoc_macro(m, c, ln, 1, &i, buf)) goto err; return(1);