blob: e3b24bfc804c3681d5b774bf4c023a4360e2487c [file] [log] [blame]
Rob Herring7a5277a2017-01-04 10:45:20 -06001#!/usr/bin/env perl
Danilo Cesar Lemes de Paula5699f872015-07-28 16:45:15 -03002
Rob Herring7a5277a2017-01-04 10:45:20 -06003use warnings;
Danilo Cesar Lemes de Paula5699f872015-07-28 16:45:15 -03004use strict;
5
6## Copyright (C) 2015 Intel Corporation ##
7# ##
8## This software falls under the GNU General Public License. ##
9## Please read the COPYING file for more information ##
10#
11#
12# This software reads a XML file and a list of valid interal
13# references to replace Docbook tags with links.
14#
15# The list of "valid internal references" must be one-per-line in the following format:
16# API-struct-foo
17# API-enum-bar
18# API-my-function
19#
20# The software walks over the XML file looking for xml tags representing possible references
21# to the Document. Each reference will be cross checked against the "Valid Internal Reference" list. If
22# the referece is found it replaces its content by a <link> tag.
23#
24# usage:
25# kernel-doc-xml-ref -db filename
26# xml filename > outputfile
27
28# read arguments
29if ($#ARGV != 2) {
30 usage();
31}
32
33#Holds the database filename
34my $databasefile;
35my @database;
36
37#holds the inputfile
38my $inputfile;
39my $errors = 0;
40
41my %highlights = (
42 "<function>(.*?)</function>",
43 "\"<function>\" . convert_function(\$1, \$line) . \"</function>\"",
44 "<structname>(.*?)</structname>",
45 "\"<structname>\" . convert_struct(\$1) . \"</structname>\"",
46 "<funcdef>(.*?)<function>(.*?)</function></funcdef>",
47 "\"<funcdef>\" . convert_param(\$1) . \"<function>\$2</function></funcdef>\"",
48 "<paramdef>(.*?)<parameter>(.*?)</parameter></paramdef>",
49 "\"<paramdef>\" . convert_param(\$1) . \"<parameter>\$2</parameter></paramdef>\"");
50
51while($ARGV[0] =~ m/^-(.*)/) {
52 my $cmd = shift @ARGV;
53 if ($cmd eq "-db") {
54 $databasefile = shift @ARGV
55 } else {
56 usage();
57 }
58}
59$inputfile = shift @ARGV;
60
61sub open_database {
62 open (my $handle, '<', $databasefile) or die "Cannot open $databasefile";
63 chomp(my @lines = <$handle>);
64 close $handle;
65
66 @database = @lines;
67}
68
69sub process_file {
70 open_database();
71
72 my $dohighlight;
73 foreach my $pattern (keys %highlights) {
74 $dohighlight .= "\$line =~ s:$pattern:$highlights{$pattern}:eg;\n";
75 }
76
77 open(FILE, $inputfile) or die("Could not open $inputfile") or die ("Cannot open $inputfile");
78 foreach my $line (<FILE>) {
79 eval $dohighlight;
80 print $line;
81 }
82}
83
84sub trim($_)
85{
86 my $str = $_[0];
87 $str =~ s/^\s+|\s+$//g;
88 return $str
89}
90
91sub has_key_defined($_)
92{
93 if ( grep( /^$_[0]$/, @database)) {
94 return 1;
95 }
96 return 0;
97}
98
99# Gets a <function> content and add it a hyperlink if possible.
100sub convert_function($_)
101{
102 my $arg = $_[0];
103 my $key = $_[0];
104
105 my $line = $_[1];
106
107 $key = trim($key);
108
109 $key =~ s/[^A-Za-z0-9]/-/g;
110 $key = "API-" . $key;
111
112 # We shouldn't add links to <funcdef> prototype
113 if (!has_key_defined($key) || $line =~ m/\s+<funcdef/i) {
114 return $arg;
115 }
116
117 my $head = $arg;
118 my $tail = "";
119 if ($arg =~ /(.*?)( ?)$/) {
120 $head = $1;
121 $tail = $2;
122 }
123 return "<link linkend=\"$key\">$head</link>$tail";
124}
125
126# Converting a struct text to link
127sub convert_struct($_)
128{
129 my $arg = $_[0];
130 my $key = $_[0];
131 $key =~ s/(struct )?(\w)/$2/g;
132 $key =~ s/[^A-Za-z0-9]/-/g;
133 $key = "API-struct-" . $key;
134
135 if (!has_key_defined($key)) {
136 return $arg;
137 }
138
139 my ($head, $tail) = split_pointer($arg);
140 return "<link linkend=\"$key\">$head</link>$tail";
141}
142
143# Identify "object *" elements
144sub split_pointer($_)
145{
146 my $arg = $_[0];
147 if ($arg =~ /(.*?)( ?\* ?)/) {
148 return ($1, $2);
149 }
150 return ($arg, "");
151}
152
153sub convert_param($_)
154{
155 my $type = $_[0];
156 my $keyname = convert_key_name($type);
157
158 if (!has_key_defined($keyname)) {
159 return $type;
160 }
161
162 my ($head, $tail) = split_pointer($type);
163 return "<link linkend=\"$keyname\">$head</link>$tail";
164
165}
166
167# DocBook links are in the API-<TYPE>-<STRUCT-NAME> format
168# This method gets an element and returns a valid DocBook reference for it.
169sub convert_key_name($_)
170{
171 #Pattern $2 is optional and might be uninitialized
172 no warnings 'uninitialized';
173
174 my $str = $_[0];
175 $str =~ s/(const|static)? ?(struct)? ?([a-zA-Z0-9_]+) ?(\*|&)?/$2 $3/g ;
176
177 # trim
178 $str =~ s/^\s+|\s+$//g;
179
180 # spaces and _ to -
181 $str =~ s/[^A-Za-z0-9]/-/g;
182
183 return "API-" . $str;
184}
185
186sub usage {
187 print "Usage: $0 -db database filename\n";
188 print " xml source file(s) > outputfile\n";
189 exit 1;
190}
191
192# starting point
193process_file();
194
195if ($errors) {
196 print STDERR "$errors errors\n";
197}
198
199exit($errors);