Patch for perl.pod
[p5sagit/p5-mst-13.2.git] / pod / pod2man.PL
CommitLineData
4633a7c4 1#!/usr/local/bin/perl
2
3use Config;
4use File::Basename qw(&basename &dirname);
5
6# List explicitly here the variables you want Configure to
7# generate. Metaconfig only looks for shell variables, so you
8# have to mention them as if they were shell variables, not
9# %Config entries. Thus you write
10# $startperl
2e4a4f55 11# $man3ext
4633a7c4 12# to ensure Configure will look for $Config{startperl}.
13
14# This forces PL files to create target in same directory as PL file.
15# This is so that make depend always knows where to find PL derivatives.
44a8e56a 16chdir dirname($0);
17$file = basename($0, '.PL');
774d564b 18$file .= '.com' if $^O eq 'VMS';
4633a7c4 19
20open OUT,">$file" or die "Can't create $file: $!";
21
22print "Extracting $file (with variable substitutions)\n";
23
24# In this section, perl variables will be expanded during extraction.
25# You can use $Config{...} to use Configure variables.
26
27print OUT <<"!GROK!THIS!";
5f05dabc 28$Config{startperl}
29 eval 'exec $Config{perlpath} -S \$0 \${1+"\$@"}'
30 if \$running_under_some_shell;
2e4a4f55 31
32\$DEF_PM_SECTION = '$Config{man3ext}' || '3';
5d94fbed 33!GROK!THIS!
34
4633a7c4 35# In the following, perl variables are not expanded during extraction.
36
37print OUT <<'!NO!SUBS!';
cb1a09d0 38
39=head1 NAME
40
41pod2man - translate embedded Perl pod directives into man pages
42
43=head1 SYNOPSIS
44
45B<pod2man>
46[ B<--section=>I<manext> ]
47[ B<--release=>I<relpatch> ]
48[ B<--center=>I<string> ]
49[ B<--date=>I<string> ]
50[ B<--fixed=>I<font> ]
51[ B<--official> ]
1e422769 52[ B<--lax> ]
cb1a09d0 53I<inputfile>
54
55=head1 DESCRIPTION
56
57B<pod2man> converts its input file containing embedded pod directives (see
58L<perlpod>) into nroff source suitable for viewing with nroff(1) or
59troff(1) using the man(7) macro set.
60
61Besides the obvious pod conversions, B<pod2man> also takes care of
62func(), func(n), and simple variable references like $foo or @bar so
63you don't have to use code escapes for them; complex expressions like
64C<$fred{'stuff'}> will still need to be escaped, though. Other nagging
65little roffish things that it catches include translating the minus in
66something like foo-bar, making a long dash--like this--into a real em
67dash, fixing up "paired quotes", putting a little space after the
68parens in something like func(), making C++ and PI look right, making
69double underbars have a little tiny space between them, making ALLCAPS
70a teeny bit smaller in troff(1), and escaping backslashes so you don't
71have to.
72
73=head1 OPTIONS
74
75=over 8
76
77=item center
78
79Set the centered header to a specific string. The default is
80"User Contributed Perl Documentation", unless the C<--official> flag is
81given, in which case the default is "Perl Programmers Reference Guide".
82
83=item date
84
85Set the left-hand footer string to this value. By default,
86the modification date of the input file will be used.
87
88=item fixed
89
90The fixed font to use for code refs. Defaults to CW.
91
92=item official
93
94Set the default header to indicate that this page is of
95the standard release in case C<--center> is not given.
96
97=item release
98
99Set the centered footer. By default, this is the current
100perl release.
101
102=item section
103
104Set the section for the C<.TH> macro. The standard conventions on
105sections are to use 1 for user commands, 2 for system calls, 3 for
106functions, 4 for devices, 5 for file formats, 6 for games, 7 for
107miscellaneous information, and 8 for administrator commands. This works
108best if you put your Perl man pages in a separate tree, like
109F</usr/local/perl/man/>. By default, section 1 will be used
110unless the file ends in F<.pm> in which case section 3 will be selected.
111
1e422769 112=item lax
113
114Don't complain when required sections aren't present.
115
cb1a09d0 116=back
117
118=head1 Anatomy of a Proper Man Page
119
120For those not sure of the proper layout of a man page, here's
121an example of the skeleton of a proper man page. Head of the
122major headers should be setout as a C<=head1> directive, and
123are historically written in the rather startling ALL UPPER CASE
124format, although this is not mandatory.
125Minor headers may be included using C<=head2>, and are
126typically in mixed case.
127
128=over 10
129
130=item NAME
131
132Mandatory section; should be a comma-separated list of programs or
133functions documented by this podpage, such as:
134
135 foo, bar - programs to do something
136
137=item SYNOPSIS
138
139A short usage summary for programs and functions, which
140may someday be deemed mandatory.
141
142=item DESCRIPTION
143
144Long drawn out discussion of the program. It's a good idea to break this
145up into subsections using the C<=head2> directives, like
146
147 =head2 A Sample Subection
148
149 =head2 Yet Another Sample Subection
150
151=item OPTIONS
152
153Some people make this separate from the description.
154
155=item RETURN VALUE
156
157What the program or function returns if successful.
158
159=item ERRORS
160
161Exceptions, return codes, exit stati, and errno settings.
162
163=item EXAMPLES
164
165Give some example uses of the program.
166
167=item ENVIRONMENT
168
169Envariables this program might care about.
170
171=item FILES
172
173All files used by the program. You should probably use the FE<lt>E<gt>
174for these.
175
176=item SEE ALSO
177
178Other man pages to check out, like man(1), man(7), makewhatis(8), or catman(8).
179
180=item NOTES
181
182Miscellaneous commentary.
183
184=item CAVEATS
185
186Things to take special care with; sometimes called WARNINGS.
187
188=item DIAGNOSTICS
189
190All possible messages the program can print out--and
191what they mean.
192
193=item BUGS
194
195Things that are broken or just don't work quite right.
196
197=item RESTRICTIONS
198
199Bugs you don't plan to fix :-)
200
201=item AUTHOR
202
203Who wrote it (or AUTHORS if multiple).
204
205=item HISTORY
206
207Programs derived from other sources sometimes have this, or
e52f39a2 208you might keep a modification log here.
cb1a09d0 209
210=back
211
212=head1 EXAMPLES
213
214 pod2man program > program.1
215 pod2man some_module.pm > /usr/perl/man/man3/some_module.3
216 pod2man --section=7 note.pod > note.7
217
218=head1 DIAGNOSTICS
219
220The following diagnostics are generated by B<pod2man>. Items
221marked "(W)" are non-fatal, whereas the "(F)" errors will cause
222B<pod2man> to immediately exit with a non-zero status.
223
224=over 4
225
226=item bad option in paragraph %d of %s: ``%s'' should be [%s]<%s>
227
228(W) If you start include an option, you should set it off
229as bold, italic, or code.
230
231=item can't open %s: %s
232
233(F) The input file wasn't available for the given reason.
234
cb1a09d0 235=item Improper man page - no dash in NAME header in paragraph %d of %s
236
237(W) The NAME header did not have an isolated dash in it. This is
238considered important.
239
240=item Invalid man page - no NAME line in %s
241
242(F) You did not include a NAME header, which is essential.
243
244=item roff font should be 1 or 2 chars, not `%s' (F)
245
246(F) The font specified with the C<--fixed> option was not
247a one- or two-digit roff font.
248
249=item %s is missing required section: %s
250
251(W) Required sections include NAME, DESCRIPTION, and if you're
252using a section starting with a 3, also a SYNOPSIS. Actually,
253not having a NAME is a fatal.
254
255=item Unknown escape: %s in %s
256
257(W) An unknown HTML entity (probably for an 8-bit character) was given via
e52f39a2 258a C<EE<lt>E<gt>> directive. Besides amp, lt, gt, and quot, recognized
cb1a09d0 259entities are Aacute, aacute, Acirc, acirc, AElig, aelig, Agrave, agrave,
260Aring, aring, Atilde, atilde, Auml, auml, Ccedil, ccedil, Eacute, eacute,
261Ecirc, ecirc, Egrave, egrave, ETH, eth, Euml, euml, Iacute, iacute, Icirc,
262icirc, Igrave, igrave, Iuml, iuml, Ntilde, ntilde, Oacute, oacute, Ocirc,
263ocirc, Ograve, ograve, Oslash, oslash, Otilde, otilde, Ouml, ouml, szlig,
264THORN, thorn, Uacute, uacute, Ucirc, ucirc, Ugrave, ugrave, Uuml, uuml,
265Yacute, yacute, and yuml.
266
267=item Unmatched =back
268
269(W) You have a C<=back> without a corresponding C<=over>.
270
271=item Unrecognized pod directive: %s
272
273(W) You specified a pod directive that isn't in the known list of
274C<=head1>, C<=head2>, C<=item>, C<=over>, C<=back>, or C<=cut>.
275
276
277=back
278
279=head1 NOTES
280
281If you would like to print out a lot of man page continuously, you
282probably want to set the C and D registers to set contiguous page
e52f39a2 283numbering and even/odd paging, at least on some versions of man(7).
cb1a09d0 284Settting the F register will get you some additional experimental
285indexing:
286
287 troff -man -rC1 -rD1 -rF1 perl.1 perldata.1 perlsyn.1 ...
288
289The indexing merely outputs messages via C<.tm> for each
290major page, section, subsection, item, and any C<XE<lt>E<gt>>
291directives.
292
293
294=head1 RESTRICTIONS
295
3dd51965 296None at this time.
cb1a09d0 297
298=head1 BUGS
299
300The =over and =back directives don't really work right. They
301take absolute positions instead of offsets, don't nest well, and
302making people count is suboptimal in any event.
303
304=head1 AUTHORS
305
306Original prototype by Larry Wall, but so massively hacked over by
307Tom Christiansen such that Larry probably doesn't recognize it anymore.
308
309=cut
a0d0e21e 310
311$/ = "";
312$cutting = 1;
313
3dd51965 314# We try first to get the version number from a local binary, in case we're
315# running an installed version of Perl to produce documentation from an
316# uninstalled newer version's pod files.
317if ($^O ne 'plan9') {
318 ($version,$patch) =
319 `\PATH=.:..:\$PATH; perl -v` =~ /version (\d\.\d{3})(?:_(\d{2}))?/;
320}
321# No luck; we'll just go with the running Perl's version
322($version,$patch) = $] =~ /^(.{5})(\d{2})?/ unless $version;
cb1a09d0 323$DEF_RELEASE = "perl $version";
324$DEF_RELEASE .= ", patch $patch" if $patch;
325
326
327sub makedate {
328 my $secs = shift;
329 my ($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime($secs);
330 my $mname = (qw{Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec})[$mon];
331 return "$mday/$mname/$year";
a0d0e21e 332}
333
cb1a09d0 334use Getopt::Long;
335
336$DEF_SECTION = 1;
337$DEF_CENTER = "User Contributed Perl Documentation";
338$STD_CENTER = "Perl Programmers Reference Guide";
339$DEF_FIXED = 'CW';
1e422769 340$DEF_LAX = 0;
cb1a09d0 341
342sub usage {
343 warn "$0: @_\n" if @_;
344 die <<EOF;
345usage: $0 [options] podpage
346Options are:
347 --section=manext (default "$DEF_SECTION")
348 --release=relpatch (default "$DEF_RELEASE")
349 --center=string (default "$DEF_CENTER")
350 --date=string (default "$DEF_DATE")
351 --fixed=font (default "$DEF_FIXED")
352 --official (default NOT)
1e422769 353 --lax (default NOT)
cb1a09d0 354EOF
355}
356
357$uok = GetOptions( qw(
358 section=s
359 release=s
360 center=s
361 date=s
362 fixed=s
363 official
1e422769 364 lax
cb1a09d0 365 help));
366
367$DEF_DATE = makedate((stat($ARGV[0]))[9] || time());
368
369usage("Usage error!") unless $uok;
370usage() if $opt_help;
371usage("Need one and only one podpage argument") unless @ARGV == 1;
372
2e4a4f55 373$section = $opt_section || ($ARGV[0] =~ /\.pm$/
374 ? $DEF_PM_SECTION : $DEF_SECTION);
cb1a09d0 375$RP = $opt_release || $DEF_RELEASE;
376$center = $opt_center || ($opt_official ? $STD_CENTER : $DEF_CENTER);
1e422769 377$lax = $opt_lax || $DEF_LAX;
cb1a09d0 378
379$CFont = $opt_fixed || $DEF_FIXED;
380
a0d0e21e 381if (length($CFont) == 2) {
382 $CFont_embed = "\\f($CFont";
cb1a09d0 383}
a0d0e21e 384elsif (length($CFont) == 1) {
385 $CFont_embed = "\\f$CFont";
cb1a09d0 386}
a0d0e21e 387else {
cb1a09d0 388 die "roff font should be 1 or 2 chars, not `$CFont_embed'";
389}
390
cb1a09d0 391$date = $opt_date || $DEF_DATE;
392
393for (qw{NAME DESCRIPTION}) {
394# for (qw{NAME DESCRIPTION AUTHOR}) {
395 $wanna_see{$_}++;
396}
397$wanna_see{SYNOPSIS}++ if $section =~ /^3/;
398
a0d0e21e 399
cb1a09d0 400$name = @ARGV ? $ARGV[0] : "<STDIN>";
401$Filename = $name;
55497cff 402if ($section =~ /^1/) {
403 require File::Basename;
404 $name = uc File::Basename::basename($name);
405}
406$name =~ s/\.(pod|p[lm])$//i;
e52f39a2 407$name =~ s(/)(::)g; # translate Getopt/Long to Getopt::Long, etc.
a0d0e21e 408
cb1a09d0 409if ($name ne 'something') {
410 FCHECK: {
411 open(F, "< $ARGV[0]") || die "can't open $ARGV[0]: $!";
412 while (<F>) {
f360dba1 413 next unless /^=\b/;
cb1a09d0 414 if (/^=head1\s+NAME\s*$/) { # an /m would forgive mistakes
415 $_ = <F>;
416 unless (/\s*-+\s+/) {
417 $oops++;
f360dba1 418 warn "$0: Improper man page - no dash in NAME header in paragraph $. of $ARGV[0]\n"
d714cd28 419 } else {
420 my @n = split /\s+-+\s+/;
421 if (@n != 2) {
422 $oops++;
423 warn "$0: Improper man page - malformed NAME header in paragraph $. of $ARGV[0]\n"
424 }
425 else {
426 %namedesc = @n;
427 }
428 }
cb1a09d0 429 last FCHECK;
430 }
f360dba1 431 next if /^=cut\b/; # DB_File and Net::Ping have =cut before NAME
1e422769 432 die "$0: Invalid man page - 1st pod line is not NAME in $ARGV[0]\n" unless $lax;
cb1a09d0 433 }
1e422769 434 die "$0: Invalid man page - no documentation in $ARGV[0]\n" unless $lax;
cb1a09d0 435 }
436 close F;
437}
438
a0d0e21e 439print <<"END";
440.rn '' }`
441''' \$RCSfile\$\$Revision\$\$Date\$
cb1a09d0 442'''
a0d0e21e 443''' \$Log\$
cb1a09d0 444'''
a0d0e21e 445.de Sh
446.br
447.if t .Sp
448.ne 5
449.PP
450\\fB\\\\\$1\\fR
451.PP
452..
453.de Sp
454.if t .sp .5v
455.if n .sp
456..
457.de Ip
458.br
459.ie \\\\n(.\$>=3 .ne \\\\\$3
460.el .ne 3
461.IP "\\\\\$1" \\\\\$2
462..
463.de Vb
464.ft $CFont
465.nf
466.ne \\\\\$1
467..
468.de Ve
469.ft R
470
471.fi
472..
473'''
474'''
475''' Set up \\*(-- to give an unbreakable dash;
476''' string Tr holds user defined translation string.
477''' Bell System Logo is used as a dummy character.
478'''
479.tr \\(*W-|\\(bv\\*(Tr
480.ie n \\{\\
481.ds -- \\(*W-
cb1a09d0 482.ds PI pi
a0d0e21e 483.if (\\n(.H=4u)&(1m=24u) .ds -- \\(*W\\h'-12u'\\(*W\\h'-12u'-\\" diablo 10 pitch
484.if (\\n(.H=4u)&(1m=20u) .ds -- \\(*W\\h'-12u'\\(*W\\h'-8u'-\\" diablo 12 pitch
485.ds L" ""
486.ds R" ""
487.ds L' '
488.ds R' '
489'br\\}
490.el\\{\\
491.ds -- \\(em\\|
492.tr \\*(Tr
493.ds L" ``
494.ds R" ''
495.ds L' `
496.ds R' '
cb1a09d0 497.ds PI \\(*p
a0d0e21e 498'br\\}
cb1a09d0 499END
500
501print <<'END';
502.\" If the F register is turned on, we'll generate
503.\" index entries out stderr for the following things:
504.\" TH Title
505.\" SH Header
506.\" Sh Subsection
507.\" Ip Item
508.\" X<> Xref (embedded
509.\" Of course, you have to process the output yourself
510.\" in some meaninful fashion.
511.if \nF \{
512.de IX
513.tm Index:\\$1\t\\n%\t"\\$2"
514..
515.nr % 0
516.rr F
517.\}
518END
519
520print <<"END";
521.TH $name $section "$RP" "$date" "$center"
522.IX Title "$name $section"
a0d0e21e 523.UC
524END
525
cb1a09d0 526while (($name, $desc) = each %namedesc) {
527 for ($name, $desc) { s/^\s+//; s/\s+$//; }
528 print qq(.IX Name "$name - $desc"\n);
529}
530
a0d0e21e 531print <<'END';
cb1a09d0 532.if n .hy 0
a0d0e21e 533.if n .na
534.ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p'
535.de CQ \" put $1 in typewriter font
536END
537print ".ft $CFont\n";
538print <<'END';
539'if n "\c
748a9306 540'if t \\&\\$1\c
541'if n \\&\\$1\c
a0d0e21e 542'if n \&"
748a9306 543\\&\\$2 \\$3 \\$4 \\$5 \\$6 \\$7
a0d0e21e 544'.ft R
545..
546.\" @(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2
547. \" AM - accent mark definitions
9430eed9 548.bd B 3
a0d0e21e 549. \" fudge factors for nroff and troff
550.if n \{\
551. ds #H 0
552. ds #V .8m
553. ds #F .3m
554. ds #[ \f1
555. ds #] \fP
556.\}
557.if t \{\
748a9306 558. ds #H ((1u-(\\\\n(.fu%2u))*.13m)
a0d0e21e 559. ds #V .6m
560. ds #F 0
561. ds #[ \&
562. ds #] \&
563.\}
564. \" simple accents for nroff and troff
565.if n \{\
566. ds ' \&
567. ds ` \&
568. ds ^ \&
569. ds , \&
570. ds ~ ~
571. ds ? ?
572. ds ! !
cb1a09d0 573. ds /
574. ds q
a0d0e21e 575.\}
576.if t \{\
748a9306 577. ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u"
578. ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u'
579. ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u'
580. ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u'
581. ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u'
a0d0e21e 582. ds ? \s-2c\h'-\w'c'u*7/10'\u\h'\*(#H'\zi\d\s+2\h'\w'c'u*8/10'
583. ds ! \s-2\(or\s+2\h'-\w'\(or'u'\v'-.8m'.\v'.8m'
748a9306 584. ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u'
a0d0e21e 585. ds q o\h'-\w'o'u*8/10'\s-4\v'.4m'\z\(*i\v'-.4m'\s+4\h'\w'o'u*8/10'
586.\}
587. \" troff and (daisy-wheel) nroff accents
748a9306 588.ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V'
a0d0e21e 589.ds 8 \h'\*(#H'\(*b\h'-\*(#H'
748a9306 590.ds v \\k:\h'-(\\n(.wu*9/10-\*(#H)'\v'-\*(#V'\*(#[\s-4v\s0\v'\*(#V'\h'|\\n:u'\*(#]
591.ds _ \\k:\h'-(\\n(.wu*9/10-\*(#H+(\*(#F*2/3))'\v'-.4m'\z\(hy\v'.4m'\h'|\\n:u'
592.ds . \\k:\h'-(\\n(.wu*8/10)'\v'\*(#V*4/10'\z.\v'-\*(#V*4/10'\h'|\\n:u'
a0d0e21e 593.ds 3 \*(#[\v'.2m'\s-2\&3\s0\v'-.2m'\*(#]
748a9306 594.ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#]
a0d0e21e 595.ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H'
748a9306 596.ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u'
a0d0e21e 597.ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#]
598.ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#]
599.ds ae a\h'-(\w'a'u*4/10)'e
600.ds Ae A\h'-(\w'A'u*4/10)'E
601.ds oe o\h'-(\w'o'u*4/10)'e
602.ds Oe O\h'-(\w'O'u*4/10)'E
603. \" corrections for vroff
748a9306 604.if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u'
605.if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u'
a0d0e21e 606. \" for low resolution devices (crt and lpr)
607.if \n(.H>23 .if \n(.V>19 \
608\{\
609. ds : e
610. ds 8 ss
611. ds v \h'-1'\o'\(aa\(ga'
612. ds _ \h'-1'^
613. ds . \h'-1'.
614. ds 3 3
615. ds o a
616. ds d- d\h'-1'\(ga
617. ds D- D\h'-1'\(hy
618. ds th \o'bp'
619. ds Th \o'LP'
620. ds ae ae
621. ds Ae AE
622. ds oe oe
623. ds Oe OE
624.\}
625.rm #[ #] #H #V #F C
626END
627
628$indent = 0;
629
8c634b6e 630$begun = "";
631
a0d0e21e 632while (<>) {
633 if ($cutting) {
634 next unless /^=/;
635 $cutting = 0;
636 }
8c634b6e 637 if ($begun) {
638 if (/^=end\s+$begun/) {
639 $begun = "";
640 }
641 elsif ($begun =~ /^(roff|man)$/) {
642 print STDOUT $_;
643 }
644 next;
645 }
a0d0e21e 646 chomp;
647
648 # Translate verbatim paragraph
649
650 if (/^\s/) {
651 @lines = split(/\n/);
652 for (@lines) {
653 1 while s
654 {^( [^\t]* ) \t ( \t* ) }
655 { $1 . ' ' x (8 - (length($1)%8) + 8 * (length($2))) }ex;
656 s/\\/\\e/g;
657 s/\A/\\&/s;
658 }
659 $lines = @lines;
660 makespace() unless $verbatim++;
661 print ".Vb $lines\n";
662 print join("\n", @lines), "\n";
663 print ".Ve\n";
664 $needspace = 0;
665 next;
666 }
667
668 $verbatim = 0;
669
8c634b6e 670 if (/^=for\s+(\S+)\s*/s) {
671 if ($1 eq "man" or $1 eq "roff") {
672 print STDOUT $',"\n\n";
673 } else {
674 # ignore unknown for
675 }
676 next;
677 }
678 elsif (/^=begin\s+(\S+)\s*/s) {
679 $begun = $1;
680 if ($1 eq "man" or $1 eq "roff") {
681 print STDOUT $'."\n\n";
682 }
683 next;
684 }
685
a0d0e21e 686 # check for things that'll hosed our noremap scheme; affects $_
687 init_noremap();
688
689 if (!/^=item/) {
690
691 # trofficate backslashes; must do it before what happens below
692 s/\\/noremap('\\e')/ge;
693
cb1a09d0 694 # first hide the escapes in case we need to
a0d0e21e 695 # intuit something and get it wrong due to fmting
696
697 s/([A-Z]<[^<>]*>)/noremap($1)/ge;
698
699 # func() is a reference to a perl function
700 s{
701 \b
702 (
703 [:\w]+ \(\)
704 )
705 } {I<$1>}gx;
706
1e2391a5 707 # func(n) is a reference to a perl function or a man page
a0d0e21e 708 s{
1e2391a5 709 ([:\w]+)
a0d0e21e 710 (
1e2391a5 711 \( [^\051]+ \)
a0d0e21e 712 )
713 } {I<$1>\\|$2}gx;
714
715 # convert simple variable references
1e2391a5 716 s/(\s+)([\$\@%][\w:]+)(?!\()/${1}C<$2>/g;
a0d0e21e 717
718 if (m{ (
719 [\-\w]+
720 \(
721 [^\051]*?
722 [\@\$,]
723 [^\051]*?
724 \)
725 )
cb1a09d0 726 }x && $` !~ /([LCI]<[^<>]*|-)$/ && !/^=\w/)
a0d0e21e 727 {
cb1a09d0 728 warn "$0: bad option in paragraph $. of $ARGV: ``$1'' should be [LCI]<$1>\n";
729 $oops++;
730 }
a0d0e21e 731
732 while (/(-[a-zA-Z])\b/g && $` !~ /[\w\-]$/) {
cb1a09d0 733 warn "$0: bad option in paragraph $. of $ARGV: ``$1'' should be [CB]<$1>\n";
734 $oops++;
735 }
a0d0e21e 736
737 # put it back so we get the <> processed again;
738 clear_noremap(0); # 0 means leave the E's
739
740 } else {
741 # trofficate backslashes
742 s/\\/noremap('\\e')/ge;
743
cb1a09d0 744 }
a0d0e21e 745
746 # need to hide E<> first; they're processed in clear_noremap
747 s/(E<[^<>]+>)/noremap($1)/ge;
748
749
750 $maxnest = 10;
751 while ($maxnest-- && /[A-Z]</) {
752
753 # can't do C font here
754 s/([BI])<([^<>]*)>/font($1) . $2 . font('R')/eg;
755
756 # files and filelike refs in italics
757 s/F<([^<>]*)>/I<$1>/g;
758
759 # no break -- usually we want C<> for this
760 s/S<([^<>]*)>/nobreak($1)/eg;
761
cb1a09d0 762 # LREF: a manpage(3f)
a0d0e21e 763 s:L<([a-zA-Z][^\s\/]+)(\([^\)]+\))?>:the I<$1>$2 manpage:g;
764
765 # LREF: an =item on another manpage
766 s{
767 L<
768 ([^/]+)
769 /
770 (
771 [:\w]+
772 (\(\))?
773 )
774 >
775 } {the C<$2> entry in the I<$1> manpage}gx;
776
777 # LREF: an =item on this manpage
778 s{
779 ((?:
780 L<
781 /
782 (
783 [:\w]+
784 (\(\))?
785 )
786 >
787 (,?\s+(and\s+)?)?
788 )+)
789 } { internal_lrefs($1) }gex;
790
791 # LREF: a =head2 (head1?), maybe on a manpage, maybe right here
792 # the "func" can disambiguate
793 s{
794 L<
795 (?:
cb1a09d0 796 ([a-zA-Z]\S+?) /
a0d0e21e 797 )?
798 "?(.*?)"?
799 >
800 }{
801 do {
802 $1 # if no $1, assume it means on this page.
803 ? "the section on I<$2> in the I<$1> manpage"
804 : "the section on I<$2>"
cb1a09d0 805 }
e52f39a2 806 }gesx; # s in case it goes over multiple lines, so . matches \n
a0d0e21e 807
808 s/Z<>/\\&/g;
809
810 # comes last because not subject to reprocessing
811 s/C<([^<>]*)>/noremap("${CFont_embed}${1}\\fR")/eg;
812 }
813
814 if (s/^=//) {
815 $needspace = 0; # Assume this.
816
817 s/\n/ /g;
818
819 ($Cmd, $_) = split(' ', $_, 2);
820
821 if (defined $_) {
822 &escapes;
823 s/"/""/g;
824 }
825
826 clear_noremap(1);
827
828 if ($Cmd eq 'cut') {
829 $cutting = 1;
830 }
831 elsif ($Cmd eq 'head1') {
cb1a09d0 832 s/\s+$//;
833 delete $wanna_see{$_} if exists $wanna_see{$_};
834 print qq{.SH "$_"\n};
835 print qq{.IX Header "$_"\n};
a0d0e21e 836 }
837 elsif ($Cmd eq 'head2') {
cb1a09d0 838 print qq{.Sh "$_"\n};
839 print qq{.IX Subsection "$_"\n};
a0d0e21e 840 }
841 elsif ($Cmd eq 'over') {
842 push(@indent,$indent);
cb1a09d0 843 $indent += ($_ + 0) || 5;
a0d0e21e 844 }
845 elsif ($Cmd eq 'back') {
846 $indent = pop(@indent);
f360dba1 847 warn "$0: Unmatched =back in paragraph $. of $ARGV\n" unless defined $indent;
a0d0e21e 848 $needspace = 1;
849 }
850 elsif ($Cmd eq 'item') {
851 s/^\*( |$)/\\(bu$1/g;
6ea29bdc 852 # if you know how to get ":s please do
853 s/\\\*\(L"([^"]+?)\\\*\(R"/'$1'/g;
854 s/\\\*\(L"([^"]+?)""/'$1'/g;
855 s/[^"]""([^"]+?)""[^"]/'$1'/g;
856 # here do something about the $" in perlvar?
a0d0e21e 857 print STDOUT qq{.Ip "$_" $indent\n};
cb1a09d0 858 print qq{.IX Item "$_"\n};
a0d0e21e 859 }
cb1a09d0 860 elsif ($Cmd eq 'pod') {
861 # this is just a comment
862 }
a0d0e21e 863 else {
f360dba1 864 warn "$0: Unrecognized pod directive in paragraph $. of $ARGV: $Cmd\n";
a0d0e21e 865 }
866 }
867 else {
868 if ($needspace) {
869 &makespace;
870 }
871 &escapes;
872 clear_noremap(1);
873 print $_, "\n";
874 $needspace = 1;
875 }
876}
877
878print <<"END";
879
880.rn }` ''
881END
882
1e422769 883if (%wanna_see && !$lax) {
cb1a09d0 884 @missing = keys %wanna_see;
885 warn "$0: $Filename is missing required section"
886 . (@missing > 1 && "s")
887 . ": @missing\n";
888 $oops++;
889}
890
891exit;
892#exit ($oops != 0);
893
a0d0e21e 894#########################################################################
895
896sub nobreak {
897 my $string = shift;
898 $string =~ s/ /\\ /g;
899 $string;
900}
901
902sub escapes {
903
cb1a09d0 904 s/X<(.*?)>/mkindex($1)/ge;
905
a0d0e21e 906 # translate the minus in foo-bar into foo\-bar for roff
907 s/([^0-9a-z-])-([^-])/$1\\-$2/g;
908
909 # make -- into the string version \*(-- (defined above)
910 s/\b--\b/\\*(--/g;
911 s/"--([^"])/"\\*(--$1/g; # should be a better way
912 s/([^"])--"/$1\\*(--"/g;
913
914 # fix up quotes; this is somewhat tricky
915 if (!/""/) {
916 s/(^|\s)(['"])/noremap("$1\\*(L$2")/ge;
917 s/(['"])($|[\-\s,;\\!?.])/noremap("\\*(R$1$2")/ge;
918 }
919
920 #s/(?!")(?:.)--(?!")(?:.)/\\*(--/g;
921 #s/(?:(?!")(?:.)--(?:"))|(?:(?:")--(?!")(?:.))/\\*(--/g;
cb1a09d0 922
a0d0e21e 923
924 # make sure that func() keeps a bit a space tween the parens
925 ### s/\b\(\)/\\|()/g;
926 ### s/\b\(\)/(\\|)/g;
927
928 # make C++ into \*C+, which is a squinched version (defined above)
929 s/\bC\+\+/\\*(C+/g;
930
931 # make double underbars have a little tiny space between them
932 s/__/_\\|_/g;
933
cb1a09d0 934 # PI goes to \*(PI (defined above)
a0d0e21e 935 s/\bPI\b/noremap('\\*(PI')/ge;
936
937 # make all caps a teeny bit smaller, but don't muck with embedded code literals
938 my $hidCFont = font('C');
939 if ($Cmd !~ /^head1/) { # SH already makes smaller
940 # /g isn't enough; 1 while or we'll be off
941
942# 1 while s{
943# (?!$hidCFont)(..|^.|^)
944# \b
945# (
946# [A-Z][\/A-Z+:\-\d_$.]+
947# )
948# (s?)
949# \b
950# } {$1\\s-1$2\\s0}gmox;
951
952 1 while s{
953 (?!$hidCFont)(..|^.|^)
954 (
955 \b[A-Z]{2,}[\/A-Z+:\-\d_\$]*\b
956 )
cb1a09d0 957 } {
a0d0e21e 958 $1 . noremap( '\\s-1' . $2 . '\\s0' )
959 }egmox;
960
961 }
962}
963
964# make troff just be normal, but make small nroff get quoted
965# decided to just put the quotes in the text; sigh;
966sub ccvt {
1e422769 967 local($_,$prev) = @_;
a0d0e21e 968 noremap(qq{.CQ "$_" \n\\&});
cb1a09d0 969}
a0d0e21e 970
971sub makespace {
972 if ($indent) {
973 print ".Sp\n";
974 }
975 else {
976 print ".PP\n";
977 }
978}
979
cb1a09d0 980sub mkindex {
981 my ($entry) = @_;
982 my @entries = split m:\s*/\s*:, $entry;
983 print ".IX Xref ";
984 for $entry (@entries) {
985 print qq("$entry" );
986 }
987 print "\n";
988 return '';
989}
990
a0d0e21e 991sub font {
992 local($font) = shift;
993 return '\\f' . noremap($font);
cb1a09d0 994}
a0d0e21e 995
996sub noremap {
997 local($thing_to_hide) = shift;
998 $thing_to_hide =~ tr/\000-\177/\200-\377/;
999 return $thing_to_hide;
cb1a09d0 1000}
a0d0e21e 1001
1002sub init_noremap {
3dd51965 1003 # escape high bit characters in input stream
1004 s/([\200-\377])/"E<".ord($1).">"/ge;
cb1a09d0 1005}
a0d0e21e 1006
1007sub clear_noremap {
1008 my $ready_to_print = $_[0];
1009
1010 tr/\200-\377/\000-\177/;
1011
1012 # trofficate backslashes
1013 # s/(?!\\e)(?:..|^.|^)\\/\\e/g;
1014
1015 # now for the E<>s, which have been hidden until now
1016 # otherwise the interative \w<> processing would have
1017 # been hosed by the E<gt>
1018 s {
3dd51965 1019 E<
1020 (
1021 ( \d + )
1022 | ( [A-Za-z]+ )
1023 )
a0d0e21e 1024 >
cb1a09d0 1025 } {
3dd51965 1026 do {
1027 defined $2
1028 ? chr($2)
1029 :
1030 exists $HTML_Escapes{$3}
1031 ? do { $HTML_Escapes{$3} }
a0d0e21e 1032 : do {
f360dba1 1033 warn "$0: Unknown escape in paragraph $. of $ARGV: ``$&''\n";
a0d0e21e 1034 "E<$1>";
cb1a09d0 1035 }
1036 }
a0d0e21e 1037 }egx if $ready_to_print;
cb1a09d0 1038}
a0d0e21e 1039
1040sub internal_lrefs {
1041 local($_) = shift;
1042
1043 s{L</([^>]+)>}{$1}g;
1044 my(@items) = split( /(?:,?\s+(?:and\s+)?)/ );
1045 my $retstr = "the ";
1046 my $i;
1047 for ($i = 0; $i <= $#items; $i++) {
1048 $retstr .= "C<$items[$i]>";
1049 $retstr .= ", " if @items > 2 && $i != $#items;
1050 $retstr .= " and " if $i+2 == @items;
cb1a09d0 1051 }
a0d0e21e 1052
1053 $retstr .= " entr" . ( @items > 1 ? "ies" : "y" )
e52f39a2 1054 . " elsewhere in this document "; # terminal space to avoid words running together (pattern used strips terminal spaces)
a0d0e21e 1055
1056 return $retstr;
1057
cb1a09d0 1058}
a0d0e21e 1059
1060BEGIN {
1061%HTML_Escapes = (
1062 'amp' => '&', # ampersand
1063 'lt' => '<', # left chevron, less-than
1064 'gt' => '>', # right chevron, greater-than
1065 'quot' => '"', # double quote
1066
1067 "Aacute" => "A\\*'", # capital A, acute accent
1068 "aacute" => "a\\*'", # small a, acute accent
1069 "Acirc" => "A\\*^", # capital A, circumflex accent
1070 "acirc" => "a\\*^", # small a, circumflex accent
1071 "AElig" => '\*(AE', # capital AE diphthong (ligature)
1072 "aelig" => '\*(ae', # small ae diphthong (ligature)
1073 "Agrave" => "A\\*`", # capital A, grave accent
1074 "agrave" => "A\\*`", # small a, grave accent
1075 "Aring" => 'A\\*o', # capital A, ring
1076 "aring" => 'a\\*o', # small a, ring
1077 "Atilde" => 'A\\*~', # capital A, tilde
1078 "atilde" => 'a\\*~', # small a, tilde
1079 "Auml" => 'A\\*:', # capital A, dieresis or umlaut mark
1080 "auml" => 'a\\*:', # small a, dieresis or umlaut mark
1081 "Ccedil" => 'C\\*,', # capital C, cedilla
1082 "ccedil" => 'c\\*,', # small c, cedilla
1083 "Eacute" => "E\\*'", # capital E, acute accent
1084 "eacute" => "e\\*'", # small e, acute accent
1085 "Ecirc" => "E\\*^", # capital E, circumflex accent
1086 "ecirc" => "e\\*^", # small e, circumflex accent
1087 "Egrave" => "E\\*`", # capital E, grave accent
1088 "egrave" => "e\\*`", # small e, grave accent
1089 "ETH" => '\\*(D-', # capital Eth, Icelandic
1090 "eth" => '\\*(d-', # small eth, Icelandic
1091 "Euml" => "E\\*:", # capital E, dieresis or umlaut mark
1092 "euml" => "e\\*:", # small e, dieresis or umlaut mark
1093 "Iacute" => "I\\*'", # capital I, acute accent
1094 "iacute" => "i\\*'", # small i, acute accent
1095 "Icirc" => "I\\*^", # capital I, circumflex accent
1096 "icirc" => "i\\*^", # small i, circumflex accent
1097 "Igrave" => "I\\*`", # capital I, grave accent
1098 "igrave" => "i\\*`", # small i, grave accent
1099 "Iuml" => "I\\*:", # capital I, dieresis or umlaut mark
1100 "iuml" => "i\\*:", # small i, dieresis or umlaut mark
1101 "Ntilde" => 'N\*~', # capital N, tilde
1102 "ntilde" => 'n\*~', # small n, tilde
1103 "Oacute" => "O\\*'", # capital O, acute accent
1104 "oacute" => "o\\*'", # small o, acute accent
1105 "Ocirc" => "O\\*^", # capital O, circumflex accent
1106 "ocirc" => "o\\*^", # small o, circumflex accent
1107 "Ograve" => "O\\*`", # capital O, grave accent
1108 "ograve" => "o\\*`", # small o, grave accent
1109 "Oslash" => "O\\*/", # capital O, slash
1110 "oslash" => "o\\*/", # small o, slash
1111 "Otilde" => "O\\*~", # capital O, tilde
1112 "otilde" => "o\\*~", # small o, tilde
1113 "Ouml" => "O\\*:", # capital O, dieresis or umlaut mark
1114 "ouml" => "o\\*:", # small o, dieresis or umlaut mark
1115 "szlig" => '\*8', # small sharp s, German (sz ligature)
1116 "THORN" => '\\*(Th', # capital THORN, Icelandic
1117 "thorn" => '\\*(th',, # small thorn, Icelandic
1118 "Uacute" => "U\\*'", # capital U, acute accent
1119 "uacute" => "u\\*'", # small u, acute accent
1120 "Ucirc" => "U\\*^", # capital U, circumflex accent
1121 "ucirc" => "u\\*^", # small u, circumflex accent
1122 "Ugrave" => "U\\*`", # capital U, grave accent
1123 "ugrave" => "u\\*`", # small u, grave accent
1124 "Uuml" => "U\\*:", # capital U, dieresis or umlaut mark
1125 "uuml" => "u\\*:", # small u, dieresis or umlaut mark
1126 "Yacute" => "Y\\*'", # capital Y, acute accent
1127 "yacute" => "y\\*'", # small y, acute accent
1128 "yuml" => "y\\*:", # small y, dieresis or umlaut mark
1129);
1130}
cb1a09d0 1131
5d94fbed 1132!NO!SUBS!
4633a7c4 1133
1134close OUT or die "Can't close $file: $!";
1135chmod 0755, $file or die "Can't reset permissions for $file: $!\n";
1136exec("$Config{'eunicefix'} $file") if $Config{'eunicefix'} ne ':';