groff
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Using tbl(1) for structure definitions


From: G. Branden Robinson
Subject: Re: Using tbl(1) for structure definitions
Date: Tue, 26 Jul 2022 19:12:29 -0500

Hi Alex,

At 2022-07-26T21:33:07+0200, Alejandro Colomar wrote:
> I've already read all that was relevant to me from tbl(1) regarding
> what I had in mind: documenting structures.

Okay.  Apart from those two nits I didn't get any other feedback from
you, did you find the document clear and satisfactory?

> I haven't seen any mention to tables having a leading blank line, yet
> I couldn't get rid of it without resorting to .PD.

You've turned over an ugly groff rock.

The extra line comes from groff man(7)'s `TS` macro.

.\" Start table.
.de1 TS
.  \" If continuous rendering, tell tbl not to use keeps.
.  ie \\n[cR] .nr 3usekeeps 0
.  el         .nr 3usekeeps 1
.  sp \\n[PD]u
.  if \\n[an-is-output-html] \{\
.    nr an-TS-ll \\n[.l]
.    ll 1000n
.  \}
.  HTML-IMAGE
..

Your first instinct might be to say, "Hey!  Get out of here with that
`sp` request!"

Your instinct will leave you unhappy the first time you render a boxed
table to a terminal.  The line at the top of the table will overlap the
glyphs on the line of text _above_ the table.

The macro package doesn't have anyway of knowing whether the table is
boxed or not.  Though it does occur to me, we could add a register for
this...

But this is just a symptom of a bigger architectural issue with tbl(1)
as implemented by groff.  It assumes that all rules, horizontal and
vertical,  are (practically) zero-width.  For typesetter devices this is
true.  But for terminals they eat an entire character cell, which is
_huge_, relatively speaking.

This causes all sorts of grief that I have catalogued in Savannah.

https://savannah.gnu.org/bugs/index.php?62471
https://savannah.gnu.org/bugs/index.php?62265

There's also an older report that hints at trouble.

https://savannah.gnu.org/bugs/index.php?49390

Some time back I had an exchange with you and/or Michael about the
origin of the 78-column rendering limit in man pages.  (In other words,
why not 80?)  I have since found out what it really was--apparently, a
workaround for groff tbl behavior.  And maybe other tbl programs, too.
tbl relies on the output driver to handle the drawing of intersections
between lines, like the corners of table boxes.  On typesetters this is
trivial: you just draw the lines.  On terminals, you have to do
collision detection!  You have to determine that a horizontal rule is
overlapping a vertical rule, and replace that character cell's contents
with a glyph indicating the intersection (and a lookup table for whether
to imply that the lines continue to the next cell).  This is a big pain
in the ass and supporting intersection of double lines, with themselves
and with single lines, would only make it worse, which is why doublebox
tables are not implemented on terminal devices.

https://savannah.gnu.org/bugs/index.php?43637

And it isn't just boxes that are affected.

https://savannah.gnu.org/bugs/index.php?43636

If you ask tbl to draw a horizontal rule across a table that is exactly
78n wide, you will get a 79n rule.  (See attachment.)  tbl deliberately
overdraws it because it makes the collision detection done by grotty(1)
feasible in more complicated cases.

I want to fix this.  Lord, I do.  But to date, the source of tbl, along
with that of the various pieces of grothml, have proven the most
challenging to my understanding.  It may happen, but likely not soon.

> Let me know if I'm doing something wrong, or if you would improve
> anything.  I come up with the following code.

I despair of the fact that you're going to get BLITZED with CHECKSTYLE
warnings, which I know you use, due to your leverage of `PD`.  I
therefore think I would rather alter tbl(1) to set a register indicating
that the table is boxed and will therefore need an extra vee of space at
the top and bottom on terminal devices.  an.tmac can straightforwardly
test this.  `TB` sounds like a name that might already be employed by
user documents, so I'm thinking `T_`, to suggest a horizontal line
having to to with tbl(1).

(It _appears_ to me, having done some quick experimentation with the
attachment, that horizontally-ruled table rows, while they are too wide,
do not cause vertical space accounting issues.)

That would enable a workaround.  And it need not be a temporary hack,
even if I deeply alter the architecture of tbl as I think is necessary
to resolve those Savannah tickets: this information might be useful for
macro packages in general.  They might want to similarly adjust vertical
spacing before a table depending on whether it's boxed.  Even documents
for other full-service macro packages rendering to typesetters might
want to take advantage of this.  (ms(7), however, manages different
registers for display distance and paragraph distance.)  If they don't,
nothing changes and nothing is lost, except a weird register name
employed by the tbl preprocessor.  Two others, `T.` and `#T`, spent 30
years undocumented until my tbl(1) page rewrite.

> diff --git a/man2type/open_how.2type b/man2type/open_how.2type
> index e058c08dc..f7b0aea42 100644
> --- a/man2type/open_how.2type
> +++ b/man2type/open_how.2type
> @@ -13,9 +13,14 @@ Linux kernel headers
>  .B #include <linux/openat2.h>
>  .PP
>  .B struct open_how {
> -.BR "    u64  flags;" "    /* " O_ "* flags */"
> -.BR "    u64  mode;" "     /* Mode for " O_ { CREAT , TMPFILE "} */"
> -.BR "    u64  resolve;" "  /* " RESOLVE_ "* flags */"
> +.PD 0
> +.TS
> +l lB lB l.

I take it you didn't care for my convention, shown in the man page, of
using capitals for the column classifier and lowercase for modifiers...

> +\&     u64     flags;  /* \fBO_\fP* flags */
> +\&     u64     mode;   /* Mode for \fBO_\fP{\fBCREAT\fP,\fBTMPFILE\fP} */
> +\&     u64     resolve;        /* \fBRESOLVE_\fP* flags */
> +.PD
> +.TE

I sure do wince at all those font escapes.  You don't _have_ to use
them, you know.  You could make the comment fields text blocks.  This
would enable you to use man(7) font macros, and, perhaps even more
importantly, this will make them flexible to different terminal line
lengths, and adaptable to contributors that get carried away with
excessively long comments.  They will degrade cleanly, heightening the
row (and even aligning with themselves!) instead of overrunning the
right margin or terminal width.

Let me also suggest that you can right-align the column with the data
type.

My proposal, forgetting about the vertical space issue discussed at
length above, is as follows.  Tabs are indicated in this email with →.

.TS
Rb Lb L.
u64→flags;→T{
/*
.BR O_ *
flags */
T}
u64→mode;→T{
/* Mode for
.BR O_ { CREAT , TMPFILE }
*/
T}
u64→resolve;→T{
/*
.BR RESOLVE_ *
flags */
T}
.TE

I've also attached the file I used to experiment with horizontal rule
placement and the "box" option.

Regards,
Branden

Attachment: 78-char-table.roff
Description: Text Data

Attachment: crete.man
Description: Unix manual page

Attachment: signature.asc
Description: PGP signature


reply via email to

[Prev in Thread] Current Thread [Next in Thread]