diff options
-rw-r--r-- | regress/roff/ce/Makefile | 9 | ||||
-rw-r--r-- | regress/roff/ce/break.in | 33 | ||||
-rw-r--r-- | regress/roff/ce/break.out_ascii | 24 | ||||
-rw-r--r-- | regress/tbl/macro/Makefile | 13 | ||||
-rw-r--r-- | regress/tbl/macro/nested.out_lint | 2 | ||||
-rw-r--r-- | regress/tbl/macro/req.in | 30 | ||||
-rw-r--r-- | regress/tbl/macro/req.out_ascii | 18 | ||||
-rw-r--r-- | regress/tbl/macro/req.out_lint | 5 | ||||
-rw-r--r-- | roff.c | 69 |
9 files changed, 160 insertions, 43 deletions
diff --git a/regress/roff/ce/Makefile b/regress/roff/ce/Makefile index 2024bdce..2528847e 100644 --- a/regress/roff/ce/Makefile +++ b/regress/roff/ce/Makefile @@ -1,5 +1,10 @@ -# $OpenBSD: Makefile,v 1.1 2019/01/04 01:06:44 schwarze Exp $ +# $OpenBSD: Makefile,v 1.2 2022/04/30 18:46:16 schwarze Exp $ -REGRESS_TARGETS = basic +REGRESS_TARGETS = basic break + +# mandoc defect: +# - For now, high level macros break .ce and .rj blocks. + +SKIP_GROFF = break .include <bsd.regress.mk> diff --git a/regress/roff/ce/break.in b/regress/roff/ce/break.in new file mode 100644 index 00000000..69dc99c4 --- /dev/null +++ b/regress/roff/ce/break.in @@ -0,0 +1,33 @@ +.\" $OpenBSD: break.in,v 1.1 2022/04/30 18:46:16 schwarze Exp $ +.TH CE-BREAK 1 "April 30, 2022" +.SH NAME +ce-break \- centering requests broken by high-level macros +.SH DESCRIPTION +initial +text +.ce 3 +Text centered with the .ce request is +.I not +filled. +.rj 4 +Text adjusted to the right margin +works in just the same way and is +.I not +filled either. +.ce +High-level macros break centering even in a +.if 1 .I conditional +block. +.PP +.nf +Now entering +explicit no-fill mode. +.ce 3 +Text is still +.I not +filled. +.PP +.fi +final +text +in fill mode diff --git a/regress/roff/ce/break.out_ascii b/regress/roff/ce/break.out_ascii new file mode 100644 index 00000000..8572cc0a --- /dev/null +++ b/regress/roff/ce/break.out_ascii @@ -0,0 +1,24 @@ +CE-BREAK(1) General Commands Manual CE-BREAK(1) + +NNAAMMEE + ce-break - centering requests broken by high-level macros + +DDEESSCCRRIIPPTTIIOONN + initial text + Text centered with the .ce request is + _n_o_t filled. + Text adjusted to the right margin + works in just the same way and is + _n_o_t filled either. + High-level macros break centering even in a + _c_o_n_d_i_t_i_o_n_a_l block. + + Now entering + explicit no-fill mode. + Text is still + _n_o_t + filled. + + final text in fill mode + +OpenBSD April 30, 2022 CE-BREAK(1) diff --git a/regress/tbl/macro/Makefile b/regress/tbl/macro/Makefile index 70ec1b33..8ea4a0d6 100644 --- a/regress/tbl/macro/Makefile +++ b/regress/tbl/macro/Makefile @@ -1,12 +1,15 @@ -# $OpenBSD: Makefile,v 1.2 2016/08/20 14:43:40 schwarze Exp $ +# $OpenBSD: Makefile,v 1.3 2022/04/30 18:46:16 schwarze Exp $ -REGRESS_TARGETS = man nested column -LINT_TARGETS = man nested +REGRESS_TARGETS = column man nested req +LINT_TARGETS = man nested req -# trivial differences to groff-1.22.3: +# mandoc defect: +# mandoc(1) ignores .br inside tbl(7) code. + +# trivial differences to groff-1.23.0: # .TS in a table causes a blank table line in GNU tbl(1), but not in mandoc. # .TS in a column list causes a blank line in mandoc, but not in GNU tbl(1). -SKIP_GROFF = nested column +SKIP_GROFF = column nested req .include <bsd.regress.mk> diff --git a/regress/tbl/macro/nested.out_lint b/regress/tbl/macro/nested.out_lint index dd044ba7..9bffbb0c 100644 --- a/regress/tbl/macro/nested.out_lint +++ b/regress/tbl/macro/nested.out_lint @@ -1 +1 @@ -mandoc: nested.in:13:4: UNSUPP: ignoring macro in table: TS +mandoc: nested.in:13:2: UNSUPP: ignoring macro in table: TS diff --git a/regress/tbl/macro/req.in b/regress/tbl/macro/req.in new file mode 100644 index 00000000..30e1fe98 --- /dev/null +++ b/regress/tbl/macro/req.in @@ -0,0 +1,30 @@ +.\" $OpenBSD: req.in,v 1.1 2022/04/30 18:46:16 schwarze Exp $ +.TH TBL-MACRO-REQ 1 "April 30, 2022" +.SH NAME +tbl-macro-req \- requests generating nodes in a table +.SH DESCRIPTION +initial text +.TS +box tab(:); +l | l . +a:b:stray +_ +c:T{ +d +e +T} +.ce +f:T{ +g +.br +h +T} +.if 1 .ce +i:T{ +j +.if 1 .br +k +T} +.TE +.PP +final text diff --git a/regress/tbl/macro/req.out_ascii b/regress/tbl/macro/req.out_ascii new file mode 100644 index 00000000..168b1ea1 --- /dev/null +++ b/regress/tbl/macro/req.out_ascii @@ -0,0 +1,18 @@ +TBL-MACRO-REQ(1) General Commands Manual TBL-MACRO-REQ(1) + +NNAAMMEE + tbl-macro-req - requests generating nodes in a table + +DDEESSCCRRIIPPTTIIOONN + initial text + + +--+-----+ + |a | b | + +--+-----+ + |c | d e | + |f | g h | + |i | j k | + +--+-----+ + final text + +OpenBSD April 30, 2022 TBL-MACRO-REQ(1) diff --git a/regress/tbl/macro/req.out_lint b/regress/tbl/macro/req.out_lint new file mode 100644 index 00000000..26af8f71 --- /dev/null +++ b/regress/tbl/macro/req.out_lint @@ -0,0 +1,5 @@ +mandoc: req.in:10:5: ERROR: ignoring extra tbl data cells: stray +mandoc: req.in:16:2: UNSUPP: ignoring macro in table: ce +mandoc: req.in:19:2: UNSUPP: ignoring macro in table: br +mandoc: req.in:22:8: UNSUPP: ignoring macro in table: ce +mandoc: req.in:25:8: UNSUPP: ignoring macro in table: br @@ -237,6 +237,7 @@ static enum roff_tok roff_parse(struct roff *, char *, int *, static int roff_parsetext(struct roff *, struct buf *, int, int *); static int roff_renamed(ROFF_ARGS); +static int roff_req_or_macro(ROFF_ARGS); static int roff_return(ROFF_ARGS); static int roff_rm(ROFF_ARGS); static int roff_rn(ROFF_ARGS); @@ -1905,7 +1906,6 @@ roff_parseln(struct roff *r, int ln, struct buf *buf, int *offs, size_t len) /* * If a scope is open, go to the child handler for that macro, * as it may want to preprocess before doing anything with it. - * Don't do so if an equation is open. */ if (r->last) { @@ -1913,19 +1913,27 @@ roff_parseln(struct roff *r, int ln, struct buf *buf, int *offs, size_t len) return (*roffs[t].sub)(r, t, buf, ln, ppos, pos, offs); } - /* No scope is open. This is a new request or macro. */ - r->options &= ~MPARSE_COMMENT; spos = pos; t = roff_parse(r, buf->buf, &pos, ln, ppos); + return roff_req_or_macro(r, t, buf, ln, spos, pos, offs); +} + +/* + * Handle a new request or macro. + * May be called outside any scope or from inside a conditional scope. + */ +static int +roff_req_or_macro(ROFF_ARGS) { - /* Tables ignore most macros. */ + /* For now, tables ignore most macros and some request. */ - if (r->tbl != NULL && (t == TOKEN_NONE || t == ROFF_TS || - t == ROFF_br || t == ROFF_ce || t == ROFF_rj || t == ROFF_sp)) { + if (r->tbl != NULL && (tok == TOKEN_NONE || tok == ROFF_TS || + tok == ROFF_br || tok == ROFF_ce || tok == ROFF_rj || + tok == ROFF_sp)) { mandoc_msg(MANDOCERR_TBLMACRO, - ln, pos, "%s", buf->buf + spos); - if (t != TOKEN_NONE) + ln, ppos, "%s", buf->buf + ppos); + if (tok != TOKEN_NONE) return ROFF_IGN; while (buf->buf[pos] != '\0' && buf->buf[pos] != ' ') pos++; @@ -1938,9 +1946,9 @@ roff_parseln(struct roff *r, int ln, struct buf *buf, int *offs, size_t len) /* For now, let high level macros abort .ce mode. */ - if (ctl && roffce_node != NULL && - (t == TOKEN_NONE || t == ROFF_Dd || t == ROFF_EQ || - t == ROFF_TH || t == ROFF_TS)) { + if (roffce_node != NULL && + (tok == TOKEN_NONE || tok == ROFF_Dd || tok == ROFF_EQ || + tok == ROFF_TH || tok == ROFF_TS)) { r->man->last = roffce_node; r->man->next = ROFF_NEXT_SIBLING; roffce_lines = 0; @@ -1952,12 +1960,12 @@ roff_parseln(struct roff *r, int ln, struct buf *buf, int *offs, size_t len) * Let the standard macro set parsers handle it. */ - if (t == TOKEN_NONE) + if (tok == TOKEN_NONE) return ROFF_CONT; - /* Execute a roff request or a user defined macro. */ + /* Execute a roff request or a user-defined macro. */ - return (*roffs[t].proc)(r, t, buf, ln, spos, pos, offs); + return (*roffs[tok].proc)(r, tok, buf, ln, ppos, pos, offs); } /* @@ -2000,8 +2008,10 @@ roff_endparse(struct roff *r) } /* - * Parse a roff node's type from the input buffer. This must be in the - * form of ".foo xxx" in the usual way. + * Parse the request or macro name at buf[*pos]. + * Return ROFF_RENAMED, ROFF_USERDEF, or a ROFF_* token value. + * For empty, undefined, mdoc(7), and man(7) macros, return TOKEN_NONE. + * As a side effect, set r->current_string to the definition or to NULL. */ static enum roff_tok roff_parse(struct roff *r, char *buf, int *pos, int ln, int ppos) @@ -2393,27 +2403,18 @@ static int roff_cond_sub(ROFF_ARGS) { struct roffnode *bl; - int irc, rr; + int irc, rr, spos; enum roff_tok t; rr = 0; /* If arguments follow "\}", skip them. */ irc = roff_cond_checkend(r, tok, buf, ln, ppos, pos, &rr); + spos = pos; t = roff_parse(r, buf->buf, &pos, ln, ppos); - /* For now, let high level macros abort .ce mode. */ - - if (roffce_node != NULL && - (t == TOKEN_NONE || t == ROFF_Dd || t == ROFF_EQ || - t == ROFF_TH || t == ROFF_TS)) { - r->man->last = roffce_node; - r->man->next = ROFF_NEXT_SIBLING; - roffce_lines = 0; - roffce_node = NULL; - } - /* - * Fully handle known macros when they are structurally - * required or when the conditional evaluated to true. + * Handle requests and macros if the conditional evaluated + * to true or if they are structurally required. + * The .break request is always handled specially. */ if (t == ROFF_break) { @@ -2426,13 +2427,11 @@ roff_cond_sub(ROFF_ARGS) break; } } - } else if (t != TOKEN_NONE && - (rr || roffs[t].flags & ROFFMAC_STRUCT)) { - irc |= (*roffs[t].proc)(r, t, buf, ln, ppos, pos, offs); + } else if (rr || (t < TOKEN_NONE && roffs[t].flags & ROFFMAC_STRUCT)) { + irc |= roff_req_or_macro(r, t, buf, ln, spos, pos, offs); if (irc & ROFF_WHILE) irc &= ~(ROFF_LOOPCONT | ROFF_LOOPEXIT); - } else - irc |= rr ? ROFF_CONT : ROFF_IGN; + } return irc; } |