| #! /usr/bin/env perl |
| # Copyright 2016-2018 The OpenSSL Project Authors. All Rights Reserved. |
| # |
| # Licensed under the OpenSSL license (the "License"). You may not use |
| # this file except in compliance with the License. You can obtain a copy |
| # in the file LICENSE in the source distribution or at |
| # https://www.openssl.org/source/license.html |
| |
| use strict; |
| use warnings; |
| |
| use File::Spec::Functions; |
| use File::Basename; |
| use File::Copy; |
| use File::Path; |
| use FindBin; |
| use lib "$FindBin::Bin/perl"; |
| use OpenSSL::Glob; |
| use Getopt::Long; |
| use Pod::Usage; |
| |
| use lib '.'; |
| use configdata; |
| |
| # We know we are in the 'util' directory and that our perl modules are |
| # in util/perl |
| use lib catdir(dirname($0), "perl"); |
| use OpenSSL::Util::Pod; |
| |
| my %options = (); |
| GetOptions(\%options, |
| 'sourcedir=s', # Source directory |
| 'section=i@', # Subdirectories to look through, |
| # with associated section numbers |
| 'destdir=s', # Destination directory |
| #'in=s@', # Explicit files to process (ignores sourcedir) |
| 'type=s', # The result type, 'man' or 'html' |
| 'suffix:s', # Suffix to add to the extension. |
| # Only used with type=man |
| 'remove', # To remove files rather than writing them |
| 'dry-run|n', # Only output file names on STDOUT |
| 'debug|D+', |
| ); |
| |
| unless ($options{section}) { |
| $options{section} = [ 1, 3, 5, 7 ]; |
| } |
| unless ($options{sourcedir}) { |
| $options{sourcedir} = catdir($config{sourcedir}, "doc"); |
| } |
| pod2usage(1) unless ( defined $options{section} |
| && defined $options{sourcedir} |
| && defined $options{destdir} |
| && defined $options{type} |
| && ($options{type} eq 'man' |
| || $options{type} eq 'html') ); |
| pod2usage(1) if ( $options{type} eq 'html' |
| && defined $options{suffix} ); |
| |
| if ($options{debug}) { |
| print STDERR "DEBUG: options:\n"; |
| print STDERR "DEBUG: --sourcedir = $options{sourcedir}\n" |
| if defined $options{sourcedir}; |
| print STDERR "DEBUG: --destdir = $options{destdir}\n" |
| if defined $options{destdir}; |
| print STDERR "DEBUG: --type = $options{type}\n" |
| if defined $options{type}; |
| print STDERR "DEBUG: --suffix = $options{suffix}\n" |
| if defined $options{suffix}; |
| foreach (sort @{$options{section}}) { |
| print STDERR "DEBUG: --section = $_\n"; |
| } |
| print STDERR "DEBUG: --remove = $options{remove}\n" |
| if defined $options{remove}; |
| print STDERR "DEBUG: --debug = $options{debug}\n" |
| if defined $options{debug}; |
| print STDERR "DEBUG: --dry-run = $options{\"dry-run\"}\n" |
| if defined $options{"dry-run"}; |
| } |
| |
| my $symlink_exists = eval { symlink("",""); 1 }; |
| |
| foreach my $section (sort @{$options{section}}) { |
| my $subdir = "man$section"; |
| my $podsourcedir = catfile($options{sourcedir}, $subdir); |
| my $podglob = catfile($podsourcedir, "*.pod"); |
| |
| foreach my $podfile (glob $podglob) { |
| my $podname = basename($podfile, ".pod"); |
| my $podpath = catfile($podfile); |
| my %podinfo = extract_pod_info($podpath, |
| { debug => $options{debug}, |
| section => $section }); |
| my @podfiles = grep { $_ ne $podname } @{$podinfo{names}}; |
| |
| my $updir = updir(); |
| my $name = uc $podname; |
| my $suffix = { man => ".$podinfo{section}".($options{suffix} // ""), |
| html => ".html" } -> {$options{type}}; |
| my $generate = { man => "pod2man --name=$name --section=$podinfo{section} --center=OpenSSL --release=$config{version} \"$podpath\"", |
| html => "pod2html \"--podroot=$options{sourcedir}\" --htmldir=$updir --podpath=man1:man3:man5:man7 \"--infile=$podpath\" \"--title=$podname\" --quiet" |
| } -> {$options{type}}; |
| my $output_dir = catdir($options{destdir}, "man$podinfo{section}"); |
| my $output_file = $podname . $suffix; |
| my $output_path = catfile($output_dir, $output_file); |
| |
| if (! $options{remove}) { |
| my @output; |
| print STDERR "DEBUG: Processing, using \"$generate\"\n" |
| if $options{debug}; |
| unless ($options{"dry-run"}) { |
| @output = `$generate`; |
| map { s|href="http://man\.he\.net/(man\d/[^"]+)(?:\.html)?"|href="../$1.html"|g; } @output |
| if $options{type} eq "html"; |
| if ($options{type} eq "man") { |
| # Because some *roff parsers are more strict than others, |
| # multiple lines in the NAME section must be merged into |
| # one. |
| my $in_name = 0; |
| my $name_line = ""; |
| my @newoutput = (); |
| foreach (@output) { |
| if ($in_name) { |
| if (/^\.SH "/) { |
| $in_name = 0; |
| push @newoutput, $name_line."\n"; |
| } else { |
| chomp (my $x = $_); |
| $name_line .= " " if $name_line; |
| $name_line .= $x; |
| next; |
| } |
| } |
| if (/^\.SH +"NAME" *$/) { |
| $in_name = 1; |
| } |
| push @newoutput, $_; |
| } |
| @output = @newoutput; |
| } |
| } |
| print STDERR "DEBUG: Done processing\n" if $options{debug}; |
| |
| if (! -d $output_dir) { |
| print STDERR "DEBUG: Creating directory $output_dir\n" if $options{debug}; |
| unless ($options{"dry-run"}) { |
| mkpath $output_dir |
| or die "Trying to create directory $output_dir: $!\n"; |
| } |
| } |
| print STDERR "DEBUG: Writing $output_path\n" if $options{debug}; |
| unless ($options{"dry-run"}) { |
| open my $output_fh, '>', $output_path |
| or die "Trying to write to $output_path: $!\n"; |
| foreach (@output) { |
| print $output_fh $_; |
| } |
| close $output_fh; |
| } |
| print STDERR "DEBUG: Done writing $output_path\n" if $options{debug}; |
| } else { |
| print STDERR "DEBUG: Removing $output_path\n" if $options{debug}; |
| unless ($options{"dry-run"}) { |
| while (unlink $output_path) {} |
| } |
| } |
| print "$output_path\n"; |
| |
| foreach (@podfiles) { |
| my $link_file = $_ . $suffix; |
| my $link_path = catfile($output_dir, $link_file); |
| if (! $options{remove}) { |
| if ($symlink_exists) { |
| print STDERR "DEBUG: Linking $link_path -> $output_file\n" |
| if $options{debug}; |
| unless ($options{"dry-run"}) { |
| symlink $output_file, $link_path; |
| } |
| } else { |
| print STDERR "DEBUG: Copying $output_path to link_path\n" |
| if $options{debug}; |
| unless ($options{"dry-run"}) { |
| copy $output_path, $link_path; |
| } |
| } |
| } else { |
| print STDERR "DEBUG: Removing $link_path\n" if $options{debug}; |
| unless ($options{"dry-run"}) { |
| while (unlink $link_path) {} |
| } |
| } |
| print "$link_path -> $output_path\n"; |
| } |
| } |
| } |
| |
| __END__ |
| |
| =pod |
| |
| =head1 NAME |
| |
| process_docs.pl - A script to process OpenSSL docs |
| |
| =head1 SYNOPSIS |
| |
| B<process_docs.pl> |
| [B<--sourcedir>=I<dir>] |
| B<--destdir>=I<dir> |
| B<--type>=B<man>|B<html> |
| [B<--suffix>=I<suffix>] |
| [B<--remove>] |
| [B<--dry-run>|B<-n>] |
| [B<--debug>|B<-D>] |
| |
| =head1 DESCRIPTION |
| |
| This script looks for .pod files in the subdirectories 'apps', 'crypto' |
| and 'ssl' under the given source directory. |
| |
| The OpenSSL configuration data file F<configdata.pm> I<must> reside in |
| the current directory, I<or> perl must have the directory it resides in |
| in its inclusion array. For the latter variant, a call like this would |
| work: |
| |
| perl -I../foo util/process_docs.pl {options ...} |
| |
| =head1 OPTIONS |
| |
| =over 4 |
| |
| =item B<--sourcedir>=I<dir> |
| |
| Top directory where the source files are found. |
| |
| =item B<--destdir>=I<dir> |
| |
| Top directory where the resulting files should end up |
| |
| =item B<--type>=B<man>|B<html> |
| |
| Type of output to produce. Currently supported are man pages and HTML files. |
| |
| =item B<--suffix>=I<suffix> |
| |
| A suffix added to the extension. Only valid with B<--type>=B<man> |
| |
| =item B<--remove> |
| |
| Instead of writing the files, remove them. |
| |
| =item B<--dry-run>|B<-n> |
| |
| Do not perform any file writing, directory creation or file removal. |
| |
| =item B<--debug>|B<-D> |
| |
| Print extra debugging output. |
| |
| =back |
| |
| =head1 COPYRIGHT |
| |
| Copyright 2013-2018 The OpenSSL Project Authors. All Rights Reserved. |
| |
| Licensed under the OpenSSL license (the "License"). You may not use |
| this file except in compliance with the License. You can obtain a copy |
| in the file LICENSE in the source distribution or at |
| https://www.openssl.org/source/license.html |
| |
| =cut |