From 27be359286baae838840a62e6c36dac6b91cd810 Mon Sep 17 00:00:00 2001 From: Kristaps Dzonsons Date: Tue, 23 Mar 2010 11:30:48 +0000 Subject: Support for pod2man standard header macros (Vb, Ve, Sp). Based largely on a set of patches by Ingo Schwarze. --- man.7 | 137 ++++++++++++++++++++++++++++++--------------------------- man.c | 5 ++- man.h | 7 ++- man_action.c | 5 ++- man_html.c | 19 ++++++-- man_macro.c | 9 +++- man_term.c | 34 +++++++++----- man_validate.c | 9 ++-- 8 files changed, 137 insertions(+), 88 deletions(-) diff --git a/man.7 b/man.7 index 173adb62..c1eacb4e 100644 --- a/man.7 +++ b/man.7 @@ -1,4 +1,4 @@ -.\" $Id: man.7,v 1.56 2010/03/22 05:59:32 kristaps Exp $ +.\" $Id: man.7,v 1.57 2010/03/23 11:30:48 kristaps Exp $ .\" .\" Copyright (c) 2009 Kristaps Dzonsons .\" @@ -14,7 +14,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: March 22 2010 $ +.Dd $Mdocdate: March 23 2010 $ .Dt MAN 7 .Os . @@ -438,6 +438,7 @@ If a next-line macro is followed by a non-next-line macro, an error is raised (unless in the case of .Sx \&br , .Sx \&sp , +.Sx \&Sp , or .Sx \&na ) . .Pp @@ -448,54 +449,49 @@ The syntax is as follows: .Ed . .Pp -.Bl -column -compact -offset indent "MacroX" "ArgumentsX" "ScopeXXXXX" -.It Em Macro Ta Em Arguments Ta Em Scope -.It Sx \&B Ta n Ta next-line -.It Sx \&BI Ta n Ta current -.It Sx \&BR Ta n Ta current -.It Sx \&DT Ta 0 Ta current -.It Sx \&I Ta n Ta next-line -.It Sx \&IB Ta n Ta current -.It Sx \&IR Ta n Ta current -.It Sx \&PD Ta n Ta current -.It Sx \&R Ta n Ta next-line -.It Sx \&RB Ta n Ta current -.It Sx \&RI Ta n Ta current -.It Sx \&SB Ta n Ta next-line -.It Sx \&SM Ta n Ta next-line -.It Sx \&TH Ta >1, <6 Ta current -.It Sx \&UC Ta n Ta current -.It Sx \&br Ta 0 Ta current -.It Sx \&fi Ta 0 Ta current -.It Sx \&i Ta n Ta current -.It Sx \&na Ta 0 Ta current -.It Sx \&nf Ta 0 Ta current -.It Sx \&r Ta 0 Ta current -.It Sx \&sp Ta 1 Ta current +.Bl -column -compact -offset indent "MacroX" "ArgumentsX" "ScopeXXXXX" "CompatX" +.It Em Macro Ta Em Arguments Ta Em Scope Ta Em Notes +.It Sx \&B Ta n Ta next-line Ta \& +.It Sx \&BI Ta n Ta current Ta \& +.It Sx \&BR Ta n Ta current Ta \& +.It Sx \&DT Ta 0 Ta current Ta \& +.It Sx \&I Ta n Ta next-line Ta \& +.It Sx \&IB Ta n Ta current Ta \& +.It Sx \&IR Ta n Ta current Ta \& +.It Sx \&PD Ta n Ta current Ta compat +.It Sx \&R Ta n Ta next-line Ta \& +.It Sx \&RB Ta n Ta current Ta \& +.It Sx \&RI Ta n Ta current Ta \& +.It Sx \&SB Ta n Ta next-line Ta \& +.It Sx \&SM Ta n Ta next-line Ta \& +.It Sx \&TH Ta >1, <6 Ta current Ta \& +.It Sx \&UC Ta n Ta current Ta compat +.It Sx \&br Ta 0 Ta current Ta compat +.It Sx \&fi Ta 0 Ta current Ta compat +.It Sx \&i Ta n Ta current Ta compat +.It Sx \&na Ta 0 Ta current Ta compat +.It Sx \&nf Ta 0 Ta current Ta compat +.It Sx \&r Ta 0 Ta current Ta compat +.It Sx \&sp Ta 1 Ta current Ta compat +.It Sx \&Sp Ta 0 Ta current Ta compat +.It Sx \&Vb Ta <1 Ta current Ta compat +.It Sx \&Ve Ta 0 Ta current Ta compat .El . .Pp -The -.Sx \&PD , -.Sx \&RS , -.Sx \&RE , -.Sx \&UC , -.Sx \&br , -.Sx \&fi , -.Sx \&i , -.Sx \&na , -.Sx \&nf , -.Sx \&r , -and -.Sx \&sp -macros should not be used. They're included for compatibility. +Macros marked as +.Qq compat +are included for compatibility with the significant corpus of existing +manuals that mix dialects of roff. These macros should not be used for +portable manuals. . . .Ss Block Macros Block macros are comprised of a head and body. Like for in-line macros, the head is scoped to the current line and, in one circumstance, the -next line (the next-line stipulations for line macros apply here as -well). +next line (the next-line stipulations as in +.Sx Line Macros +apply here as well). .Pp The syntax is as follows: .Bd -literal -offset indent @@ -523,33 +519,29 @@ or No closure refers to an explicit block closing macro. . .Pp -.Bl -column "MacroX" "ArgumentsX" "Head ScopeX" "sub-sectionX" -compact -offset indent -.It Em Macro Ta Em Arguments Ta Em Head Scope Ta Em Body Scope -.It Sx \&HP Ta <2 Ta current Ta paragraph -.It Sx \&IP Ta <3 Ta current Ta paragraph -.It Sx \&LP Ta 0 Ta current Ta paragraph -.It Sx \&P Ta 0 Ta current Ta paragraph -.It Sx \&PP Ta 0 Ta current Ta paragraph -.It Sx \&RE Ta 0 Ta current Ta none -.It Sx \&RS Ta 1 Ta current Ta part -.It Sx \&SH Ta >0 Ta next-line Ta section -.It Sx \&SS Ta >0 Ta next-line Ta sub-section -.It Sx \&TP Ta n Ta next-line Ta paragraph +.Bl -column -compact -offset indent "MacroX" "ArgumentsX" "Head ScopeX" "sub-sectionX" "compatX" +.It Em Macro Ta Em Arguments Ta Em Head Scope Ta Em Body Scope Ta Em Notes +.It Sx \&HP Ta <2 Ta current Ta paragraph Ta \& +.It Sx \&IP Ta <3 Ta current Ta paragraph Ta \& +.It Sx \&LP Ta 0 Ta current Ta paragraph Ta \& +.It Sx \&P Ta 0 Ta current Ta paragraph Ta \& +.It Sx \&PP Ta 0 Ta current Ta paragraph Ta \& +.It Sx \&RE Ta 0 Ta current Ta none Ta compat +.It Sx \&RS Ta 1 Ta current Ta part Ta compat +.It Sx \&SH Ta >0 Ta next-line Ta section Ta \& +.It Sx \&SS Ta >0 Ta next-line Ta sub-section Ta \& +.It Sx \&TP Ta n Ta next-line Ta paragraph Ta \& .El +.Pp +. +Macros marked +.Qq compat +are as mentioned in +.Sx Line Macros . . .Pp If a block macro is next-line scoped, it may only be followed by in-line -macros (excluding -.Sx \&DT , -.Sx \&PD , -.Sx \&TH , -.Sx \&UC , -.Sx \&br , -.Sx \&na , -.Sx \&sp , -.Sx \&nf , -and -.Sx \&fi ) . +macros for decorating text. . . .Sh REFERENCE @@ -979,6 +971,21 @@ macro. Defaults to 1, if unspecified. See also .Sx \&br . . +.Ss \&Sp +A synonym for +.Sx \&sp +.Cm 0.5v . +. +.Ss \&Vb +A synonym for +.Sx \&nf . +Accepts an argument (the height of the formatted space) which is +disregarded. +. +.Ss \&Ve +A synonym for +.Sx \&fi . +. . .Sh COMPATIBILITY This section documents compatibility with other roff implementations, at diff --git a/man.c b/man.c index 2aee2cb5..00d42577 100644 --- a/man.c +++ b/man.c @@ -1,4 +1,4 @@ -/* $Id: man.c,v 1.51 2010/03/22 14:03:03 kristaps Exp $ */ +/* $Id: man.c,v 1.52 2010/03/23 11:30:48 kristaps Exp $ */ /* * Copyright (c) 2008, 2009 Kristaps Dzonsons * @@ -60,7 +60,8 @@ const char *const __man_macronames[MAN_MAX] = { "R", "B", "I", "IR", "RI", "na", "i", "sp", "nf", "fi", "r", "RE", - "RS", "DT", "UC", "PD" + "RS", "DT", "UC", "PD", + "Sp", "Vb", "Ve", }; const char * const *man_macronames = __man_macronames; diff --git a/man.h b/man.h index efb8568c..7a752ece 100644 --- a/man.h +++ b/man.h @@ -1,4 +1,4 @@ -/* $Id: man.h,v 1.23 2009/10/30 05:58:37 kristaps Exp $ */ +/* $Id: man.h,v 1.24 2010/03/23 11:30:48 kristaps Exp $ */ /* * Copyright (c) 2009 Kristaps Dzonsons * @@ -51,7 +51,10 @@ #define MAN_DT 29 #define MAN_UC 30 #define MAN_PD 31 -#define MAN_MAX 32 +#define MAN_Sp 32 +#define MAN_Vb 33 +#define MAN_Ve 34 +#define MAN_MAX 35 enum man_type { MAN_TEXT, diff --git a/man_action.c b/man_action.c index d481f103..7e3cde24 100644 --- a/man_action.c +++ b/man_action.c @@ -1,4 +1,4 @@ -/* $Id: man_action.c,v 1.26 2010/03/22 14:03:03 kristaps Exp $ */ +/* $Id: man_action.c,v 1.27 2010/03/23 11:30:48 kristaps Exp $ */ /* * Copyright (c) 2008, 2009 Kristaps Dzonsons * @@ -68,6 +68,9 @@ const struct actions man_actions[MAN_MAX] = { { NULL }, /* DT */ { NULL }, /* UC */ { NULL }, /* PD */ + { NULL }, /* Sp */ + { post_nf }, /* Vb */ + { post_fi }, /* Ve */ }; diff --git a/man_html.c b/man_html.c index 495a5fca..a759bd9d 100644 --- a/man_html.c +++ b/man_html.c @@ -1,4 +1,4 @@ -/* $Id: man_html.c,v 1.28 2010/03/22 14:03:03 kristaps Exp $ */ +/* $Id: man_html.c,v 1.29 2010/03/23 11:30:48 kristaps Exp $ */ /* * Copyright (c) 2008, 2009 Kristaps Dzonsons * @@ -103,6 +103,9 @@ static const struct htmlman mans[MAN_MAX] = { { man_ign_pre, NULL }, /* DT */ { man_ign_pre, NULL }, /* UC */ { man_ign_pre, NULL }, /* PD */ + { man_br_pre, NULL }, /* Sp */ + { man_ign_pre, NULL }, /* Vb */ + { NULL, NULL }, /* Vi */ }; @@ -341,10 +344,18 @@ man_br_pre(MAN_ARGS) SCALE_VS_INIT(&su, 1); - if (MAN_sp == n->tok && n->child) - a2roffsu(n->child->string, &su, SCALE_VS); - else if (MAN_br == n->tok) + switch (n->tok) { + case (MAN_Sp): + SCALE_VS_INIT(&su, 0.5); + break; + case (MAN_sp): + if (n->child) + a2roffsu(n->child->string, &su, SCALE_VS); + break; + default: su.scale = 0; + break; + } bufcat_su(h, "height", &su); PAIR_STYLE_INIT(&tag, h); diff --git a/man_macro.c b/man_macro.c index 0781bbda..1641d927 100644 --- a/man_macro.c +++ b/man_macro.c @@ -1,4 +1,4 @@ -/* $Id: man_macro.c,v 1.31 2010/03/22 05:59:32 kristaps Exp $ */ +/* $Id: man_macro.c,v 1.32 2010/03/23 11:30:48 kristaps Exp $ */ /* * Copyright (c) 2008, 2009 Kristaps Dzonsons * @@ -72,6 +72,9 @@ const struct man_macro __man_macros[MAN_MAX] = { { in_line_eoln, 0 }, /* DT */ { in_line_eoln, 0 }, /* UC */ { in_line_eoln, 0 }, /* PD */ + { in_line_eoln, MAN_NSCOPED }, /* Sp */ + { in_line_eoln, 0 }, /* Vb */ + { in_line_eoln, 0 }, /* Ve */ }; const struct man_macro * const man_macros = __man_macros; @@ -316,6 +319,10 @@ in_line_eoln(MACRO_PROT_ARGS) if (0 == w) break; + /* XXX ignore Vb arguments for now */ + if (MAN_Vb == tok) + continue; + if ( ! man_word_alloc(m, line, la, p)) return(0); } diff --git a/man_term.c b/man_term.c index 0a012d04..c15354c3 100644 --- a/man_term.c +++ b/man_term.c @@ -1,4 +1,4 @@ -/* $Id: man_term.c,v 1.56 2010/03/22 05:59:32 kristaps Exp $ */ +/* $Id: man_term.c,v 1.57 2010/03/23 11:30:48 kristaps Exp $ */ /* * Copyright (c) 2008, 2009 Kristaps Dzonsons * @@ -139,6 +139,9 @@ static const struct termact termacts[MAN_MAX] = { { pre_ign, NULL, 0 }, /* DT */ { pre_ign, NULL, 0 }, /* UC */ { pre_ign, NULL, 0 }, /* PD */ + { pre_sp, NULL, MAN_NOTEXT }, /* Sp */ + { pre_nf, NULL, 0 }, /* Vb */ + { pre_fi, NULL, 0 }, /* Ve */ }; @@ -156,6 +159,7 @@ terminal_man(void *arg, const struct man *man) if (NULL == p->symtab) switch (p->enc) { case (TERMENC_ASCII): + p->maxrmargin = 65; p->symtab = chars_init(CHARS_ASCII); break; default: @@ -248,6 +252,7 @@ static int pre_fi(DECL_ARGS) { + p->rmargin = p->maxrmargin = 65; mt->fl &= ~MANT_LITERAL; return(1); } @@ -258,9 +263,11 @@ static int pre_nf(DECL_ARGS) { + p->rmargin = p->maxrmargin = 78; term_newln(p); mt->fl |= MANT_LITERAL; - return(1); + + return(MAN_Vb != n->tok); } @@ -873,6 +880,7 @@ static void print_man_head(struct termp *p, const struct man_meta *m) { char buf[BUFSIZ], title[BUFSIZ]; + size_t buflen, titlen; p->rmargin = p->maxrmargin; p->offset = 0; @@ -880,11 +888,15 @@ print_man_head(struct termp *p, const struct man_meta *m) if (m->vol) strlcpy(buf, m->vol, BUFSIZ); + buflen = strlen(buf); snprintf(title, BUFSIZ, "%s(%d)", m->title, m->msec); + titlen = strlen(title); p->offset = 0; - p->rmargin = (p->maxrmargin - strlen(buf) + 1) / 2; + p->rmargin = 2 * (titlen+1) + buflen < p->maxrmargin ? + (p->maxrmargin - strlen(buf) + 1) / 2 : + p->maxrmargin - buflen; p->flags |= TERMP_NOBREAK | TERMP_NOSPACE; term_word(p, title); @@ -892,18 +904,20 @@ print_man_head(struct termp *p, const struct man_meta *m) p->flags |= TERMP_NOLPAD | TERMP_NOSPACE; p->offset = p->rmargin; - p->rmargin = p->maxrmargin - strlen(title); + p->rmargin = p->offset + buflen + titlen < p->maxrmargin ? + p->maxrmargin - titlen : p->maxrmargin; term_word(p, buf); term_flushln(p); - p->offset = p->rmargin; - p->rmargin = p->maxrmargin; p->flags &= ~TERMP_NOBREAK; - p->flags |= TERMP_NOLPAD | TERMP_NOSPACE; - - term_word(p, title); - term_flushln(p); + if (p->rmargin + titlen <= p->maxrmargin) { + p->flags |= TERMP_NOLPAD | TERMP_NOSPACE; + p->offset = p->rmargin; + p->rmargin = p->maxrmargin; + term_word(p, title); + term_flushln(p); + } p->rmargin = p->maxrmargin; p->offset = 0; diff --git a/man_validate.c b/man_validate.c index 4776445e..f0b8164f 100644 --- a/man_validate.c +++ b/man_validate.c @@ -1,4 +1,4 @@ -/* $Id: man_validate.c,v 1.29 2010/03/22 05:59:32 kristaps Exp $ */ +/* $Id: man_validate.c,v 1.30 2010/03/23 11:30:48 kristaps Exp $ */ /* * Copyright (c) 2008, 2009 Kristaps Dzonsons * @@ -55,7 +55,7 @@ static v_check posts_ge2_le5[] = { check_ge2, check_le5, NULL }; static v_check posts_par[] = { check_par, NULL }; static v_check posts_part[] = { check_part, NULL }; static v_check posts_sec[] = { check_sec, NULL }; -static v_check posts_sp[] = { check_le1, NULL }; +static v_check posts_le1[] = { check_le1, NULL }; static v_check pres_bline[] = { check_bline, NULL }; static const struct man_valid man_valids[MAN_MAX] = { @@ -82,7 +82,7 @@ static const struct man_valid man_valids[MAN_MAX] = { { NULL, NULL }, /* RI */ { NULL, posts_eq0 }, /* na */ { NULL, NULL }, /* i */ - { NULL, posts_sp }, /* sp */ + { NULL, posts_le1 }, /* sp */ { pres_bline, posts_eq0 }, /* nf */ { pres_bline, posts_eq0 }, /* fi */ { NULL, NULL }, /* r */ @@ -91,6 +91,9 @@ static const struct man_valid man_valids[MAN_MAX] = { { NULL, NULL }, /* DT */ { NULL, NULL }, /* UC */ { NULL, NULL }, /* PD */ + { NULL, posts_eq0 }, /* Sp */ + { pres_bline, posts_le1 }, /* Vb */ + { pres_bline, posts_eq0 }, /* Ve */ }; -- cgit v1.2.3-56-ge451