initial revision
[swftools.git] / parsedoc.pl
1 use File::Find;
2 use strict;
3
4 my $file = $ARGV[0];
5 if(!$file) {
6     print "Usage: parsedoc.pl <docfile.doc>\n";
7     exit(0);
8 }
9
10 my $paramhelp = "";
11
12 sub add_option_to_manpage
13 {
14     my $shortopt = shift;
15     my $longopt = shift;
16     my $params = shift;
17     my $doc = shift;
18     my $longdoc = shift;
19     chomp $longdoc;
20     chomp $longdoc;
21     $shortopt =~ s|-|\\-|; 
22     $params =~ s|<(.*)>|\\fI\1\\fR|;
23     $longdoc =~ s/<([a-zA-Z0-9_-]+)>/\\fI\1\\fR/;
24     #$longdoc =~ s/%/%%$1/g;
25     print manpage << "EOF"
26 .TP
27 \\fB\\-$shortopt\\fR, \\fB\\-\\-$longopt\\fR $params
28 $longdoc
29 EOF
30 ;
31 }
32
33 sub add_option_to_help
34 {
35     my $shortopt = shift;
36     my $longopt = shift;
37     my $params = shift;
38     my $doc = shift;
39     my $longdoc = shift;
40     chomp $doc;
41     chomp $doc;
42     my $s1 = " "x(2-length($shortopt));
43     my $s2 = " "x(20-length($longopt." ".$params));
44     $doc =~ s/"/\\"/g;
45     $paramhelp .= "    printf(\"-$shortopt$s1, --$longopt $params$s2$doc\\n\");\n";
46 }
47
48 sub add_header_to_manpage
49 {
50     my $package = shift;
51     my $progname = shift;
52     my $short_description = shift;
53     my $long_description = shift;
54     my $usage = shift;
55     my $date = `date +"%B %Y"`;
56     my $newusage = "";
57     chomp $date;
58
59     split(/\n/,$usage);
60     my $p  = "";
61     foreach my $u (@_) {
62         $u =~ s/%s/$progname/g;
63         $newusage .= "$p.B $u\n";
64         $p = ".PP\n";
65     }
66
67     print manpage << "EOF"
68 .TH $progname "1" "$date" "$progname" "$package"
69 .SH NAME
70 $progname - $short_description
71 .SH Synopsis
72 $newusage
73 .SH DESCRIPTION
74 $long_description
75 .SH OPTIONS
76 EOF
77 ;
78 }
79 open(fi, "$file") or die "File not found";
80
81 my $package = "swftools";
82 my $progname = $file;
83 $progname =~ s|(^/?([^/]+/))*([^/]+).doc|$3|;
84 my $path = $1;
85
86 open(manpage, ">$path$progname.1") or die;
87
88 my $usage = "";
89 my $short_description = "";
90 my $long_description  = "";
91 while(<fi>) {
92     last if(/^\s*$/);
93     s/^\s*Usage:\s*//g;
94     s/^\s*OR:\s*//g;
95     $usage .= $_;
96 }
97 while(<fi>) {
98     last if(/^\s*$/);
99     $short_description .= $_;
100 }
101 while(<fi>) {
102     last if(/^\s*$/);
103     $long_description .= $_;
104 }
105
106 add_header_to_manpage($package, $progname, $short_description, $long_description, $usage);
107
108 $_=<fi>;
109
110 my $numopts = 0;
111 my @shortopts;
112 my @longopts;
113
114 while(1) {
115     if(/^-([^\s,]+)[\s,]+--([^\s]+)(\s+(.*))?$/) {
116         my $shortopt = $1;
117         my $longopt = $2;
118         my $params = $4;
119         my $doc = "";
120         my $longdoc = "";
121         while(<fi>) {
122             last if(/^-/);
123             last if(/^\s*$/);
124             if(!$doc) {
125                 $doc .= $_;
126             } else {
127                 $longdoc .= $_;
128             }
129         }
130         $longdoc = $doc if(!$longdoc || ($longdoc =~ /^\s*$/));
131
132         $shortopts[$numopts] = $shortopt;
133         $longopts[$numopts] = $longopt;
134         $numopts++;
135
136         add_option_to_manpage($shortopt,$longopt,$params,$doc,$longdoc);
137         add_option_to_help($shortopt,$longopt,$params,$doc,$longdoc);
138         last if(eof(fi));
139         next;
140     }
141     last if(/^\s*/);
142     last if(!($_=<fi>));
143     last if(/^\s*/);
144 }
145
146 my $tail = "";
147 while(<fi>) {
148     $tail .= $_;
149 }
150
151 print manpage $tail;
152 close(manpage);
153
154
155 my $filename = "$path$progname.c";
156 my $cfile;
157 if(!open($cfile, "<$filename")) {
158     $filename = "$path$progname.cpp";
159     if(!open($cfile, "<$filename")) {
160         $filename = "$path$progname.cc";
161         if(!open($cfile, "<$filename")) {
162             $filename = "$path$progname.c++";
163             open($cfile, "<$filename") or die;
164         }
165     }
166 }
167
168 my $src="";
169 while(<$cfile>)
170 {
171     if(/void\s*args_callback_usage.*\(.*\*/) {
172         print "substituting usage in $filename\n";
173         if(!/{/) {<$cfile>;}
174         $src .= "void args_callback_usage(char *name)\n";
175         $src .= "{\n";
176         $src .= "    printf(\"\\n\");\n";
177         while(<$cfile>) {
178             last if(/}\s*$/);
179         }
180         split(/\n/,$usage);
181         my $prefix = "Usage:";
182         my $u;
183         foreach $u (@_) {
184             if($u =~ /%s/) {
185                 $src .= "    printf(\"$prefix $u\\n\", name);\n";
186             } else {
187                 $src .= "    printf(\"$prefix $u\\n\");\n";
188             }
189             $prefix = "OR:   ";
190         }
191         $src .= "    printf(\"\\n\");\n";
192
193         $src .= "$paramhelp";
194         
195         $src .= "    printf(\"\\n\");\n";
196
197         $src .= "}\n";
198         next;
199     }
200     if(/^\s*(static\s+)?(struct\s+)?options_t.*=/) {
201         print "substituting options_t in $filename\n";
202         while(<$cfile>) {
203             last if(/;$/);
204         }
205         split(/\n/,$usage);
206         $src .= "static struct options_t options[] = {\n";
207         for(my $t=0;$t<$numopts;$t++) {
208             my $s = $shortopts[$t];
209             my $l = $longopts[$t];
210             $src .= "{\"$s\", \"$l\"},\n";
211         }
212         $src .= "{0,0}\n};\n";
213         next;
214     }
215     $src .= $_;
216 }
217
218 close($cfile);
219 open($cfile, ">$filename") or die;
220 print $cfile $src;
221 close($cfile);
222