diff options
author | Ingo Schwarze <schwarze@cvs.openbsd.org> | 2018-08-21 18:15:18 +0000 |
---|---|---|
committer | Ingo Schwarze <schwarze@cvs.openbsd.org> | 2018-08-21 18:15:18 +0000 |
commit | bd19e5c0cab42e85a8a1410ea63d7f30958827b6 (patch) | |
tree | c2d44016fd1444a8cfc5f488bf4634d3b11b0c04 | |
parent | b3830ec6a8b4daa633a42abe0e23b6fd077d0501 (diff) |
Implement the \\$@ escape sequence (insert all macro arguments,
quoted) in addition to the already supported \\$* (similar, but
unquoted). Then use \\$@ to improve the implementation of
the .als request (macro alias).
Needed by groff_hdtbl(7).
Gosh, it feels like the manual pages of the groff package are
exercising every bloody roff(7) feature under the sun. In the
manual page source code itself, not merely in the implementation
of the used macro packages, that is.
-rw-r--r-- | share/man/man7/roff.7 | 9 | ||||
-rw-r--r-- | usr.bin/mandoc/roff.c | 24 |
2 files changed, 26 insertions, 7 deletions
diff --git a/share/man/man7/roff.7 b/share/man/man7/roff.7 index 219657587b8..a48c10ffb76 100644 --- a/share/man/man7/roff.7 +++ b/share/man/man7/roff.7 @@ -1,4 +1,4 @@ -.\" $OpenBSD: roff.7,v 1.81 2018/08/19 17:43:39 schwarze Exp $ +.\" $OpenBSD: roff.7,v 1.82 2018/08/21 18:15:17 schwarze Exp $ .\" .\" Copyright (c) 2010, 2011, 2012 Kristaps Dzonsons <kristaps@bsd.lv> .\" Copyright (c) 2010-2018 Ingo Schwarze <schwarze@openbsd.org> @@ -15,7 +15,7 @@ .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" -.Dd $Mdocdate: August 19 2018 $ +.Dd $Mdocdate: August 21 2018 $ .Dt ROFF 7 .Os .Sh NAME @@ -632,6 +632,8 @@ produces in the input stream, and thus in the output: \fI\^XtFree\^\fP. Each occurrence of \e\e$* is replaced with all the arguments, joined together with single space characters. +The variant \e\e$@ is similar, except that each argument is +individually quoted. .Pp Since macros and user-defined strings share a common string table, defining a macro @@ -1836,6 +1838,9 @@ Discard the rest of the physical input line and continue the logical input line on the next physical input line, joining the text on both lines together as if it were on a single input line. This is a groff extension. +.Ss \e$ Ns Ar arg +Macro argument expansion, see +.Sx de . .Ss \e% Hyphenation allowed at this point of the word; ignored by .Xr mandoc 1 . diff --git a/usr.bin/mandoc/roff.c b/usr.bin/mandoc/roff.c index ee9d45cf808..b6731170b7d 100644 --- a/usr.bin/mandoc/roff.c +++ b/usr.bin/mandoc/roff.c @@ -1,4 +1,4 @@ -/* $OpenBSD: roff.c,v 1.209 2018/08/20 17:31:44 schwarze Exp $ */ +/* $OpenBSD: roff.c,v 1.210 2018/08/21 18:15:16 schwarze Exp $ */ /* * Copyright (c) 2008-2012, 2014 Kristaps Dzonsons <kristaps@bsd.lv> * Copyright (c) 2010-2015, 2017, 2018 Ingo Schwarze <schwarze@openbsd.org> @@ -3154,7 +3154,7 @@ roff_als(ROFF_ARGS) if (oldsz == 0) return ROFF_IGN; - valsz = mandoc_asprintf(&value, ".%.*s \\$*\\\"\n", + valsz = mandoc_asprintf(&value, ".%.*s \\$@\\\"\n", (int)oldsz, oldn); roff_setstrn(&r->strtab, newn, newsz, value, valsz, 0); roff_setstrn(&r->rentab, newn, newsz, NULL, 0, 0); @@ -3378,7 +3378,7 @@ roff_userdef(ROFF_ARGS) { const char *arg[16], *ap; char *cp, *n1, *n2; - int argc, expand_count, i, ib, ie; + int argc, expand_count, i, ib, ie, quote_args; size_t asz, esz, rsz; /* @@ -3413,13 +3413,21 @@ roff_userdef(ROFF_ARGS) continue; if (*cp++ != '$') continue; - if (*cp == '*') { /* \\$* inserts all arguments */ + + quote_args = 0; + switch (*cp) { + case '@': /* \\$@ inserts all arguments, quoted */ + quote_args = 1; + /* FALLTHROUGH */ + case '*': /* \\$* inserts all arguments, unquoted */ ib = 0; ie = argc - 1; - } else { /* \\$1 .. \\$9 insert one argument */ + break; + default: /* \\$1 .. \\$9 insert one argument */ ib = ie = *cp - '1'; if (ib < 0 || ib > 8) continue; + break; } cp -= 2; @@ -3445,6 +3453,8 @@ roff_userdef(ROFF_ARGS) asz = ie > ib ? ie - ib : 0; /* for blanks */ for (i = ib; i <= ie; i++) { + if (quote_args) + asz += 2; for (ap = arg[i]; *ap != '\0'; ap++) { asz++; if (*ap == '"') @@ -3491,6 +3501,8 @@ roff_userdef(ROFF_ARGS) n2 = cp; for (i = ib; i <= ie; i++) { + if (quote_args) + *n2++ = '"'; for (ap = arg[i]; *ap != '\0'; ap++) { if (*ap == '"') { memcpy(n2, "\\(dq", 4); @@ -3498,6 +3510,8 @@ roff_userdef(ROFF_ARGS) } else *n2++ = *ap; } + if (quote_args) + *n2++ = '"'; if (i < ie) *n2++ = ' '; } |