1 #!/usr/bin/env perl
2
3 # This script cleans up the "official" Broadcom hsi_struct_defs.h file as distributed
4 # to something somewhat more programmer friendly.
5 #
6 # $FreeBSD: releng/12.0/sys/dev/bnxt/convert_hsi.pl 308696 2016-11-15 20:35:29Z shurd $
7
8 my $do_decode = 0;
9
10 if (! -f $ARGV[0]) {
11 print "Input file not specified (should be path to hsi_struct_defs.h)\n";
12 exit 1;
13 }
14
15 if (!open(IN, "<", $ARGV[0])) {
16 print "Failure to open input file\n";
17 exit 1;
18 }
19
20 if (!open(OUT, ">", "hsi_struct_def.h")) {
21 print "Failure to open output file\n";
22 exit 1;
23 }
24
25 $/=undef;
26 my $header = <IN>;
27 close IN;
28
29 print OUT <<END_OF_NOTICE;
30 /*-
31 * BSD LICENSE
32 *
33 * Copyright (c) 2016 Broadcom, All Rights Reserved.
34 * The term Broadcom refers to Broadcom Limited and/or its subsidiaries
35 *
36 * Redistribution and use in source and binary forms, with or without
37 * modification, are permitted provided that the following conditions
38 * are met:
39 * * Redistributions of source code must retain the above copyright
40 * notice, this list of conditions and the following disclaimer.
41 * * Redistributions in binary form must reproduce the above copyright
42 * notice, this list of conditions and the following disclaimer in
43 * the documentation and/or other materials provided with the
44 * distribution.
45 *
46 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
47 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
48 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
49 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
50 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
51 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
52 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
53 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
54 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
55 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
56 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
57 */
58
59 #include <sys/cdefs.h>
60 __FBSDID("\$FreeBSD\$");
61
62 END_OF_NOTICE
63
64 # Convert line endings
65 $header =~ s/\r\n/\n/gs;
66
67 # Convert arrays of two u32_t to a single uint64_t
68 $header =~ s/\bu32_t(\s+[a-zA-Z0-9_]+)\[2\]/uint64_t$1/gs;
69
70 # Convert uint32_t *_lo/uint32_t *_hi to a single uint64_t
71 $header =~ s/\bu32_t(\s+[a-zA-Z0-9_]+)_lo;\s*\r?\n\s*u32_t(\s+[a-zA-Z0-9_]+)_hi/uint64_t$1/gs;
72
73 # Convert types
74 $header =~ s/\bu([0-9]+)_t\b/uint$1_t/gs;
75
76 # Convert literals
77 $header =~ s/\b((?:0x)?[0-9a-f]+)UL/UINT32_C($1)/gs;
78
79 # Strip comments
80 #$header =~ s/^(\s*[^\/\s][^\/]+?)\s*\/\*.*?\*\/\s*?$/$1/gm;
81 #$header =~ s/[ \t]*\/\*.*?\*\/\s*?\n?//gs;
82
83 # Pack structs
84 #$header =~ s/}(\s+)([^\s]+_t[,;])/} __attribute__((packed))$1$2/gs;
85
86 # Normalize indent
87 $header =~ s/( ) +(#define)/$1$2/gs;
88 $header =~ s/^(}[^\n]*;)\n([^\n])/$1\n\n$2/gsm;
89 $header =~ s/([^\n])\n(typedef)/$1\n\n$2/gs;
90 $header =~ s/ /\t/g;
91 $header =~ s/ /\t/g;
92 $header =~ s/([^\s]\t+) +/$1/g;
93
94 # Remove typedefs and pack structs
95 $header =~ s/^typedef struct (.*?)\n{\n(.*?)}[^\n]*;/struct $1 {\n$2} __attribute__((packed));/gsm;
96
97 print OUT $header;
98 close OUT;
99
100 if ($do_decode) {
101 if(!open(OUT, ">", "hsi_struct_decode.c")) {
102 print "Failure to open decoder output file\n";
103 exit 1;
104 }
105
106 print OUT <<END_OF_NOTICE;
107 /*-
108 * BSD LICENSE
109 *
110 * Copyright (c) 2016 Broadcom, All Rights Reserved.
111 * The term Broadcom refers to Broadcom Limited and/or its subsidiaries
112 *
113 * Redistribution and use in source and binary forms, with or without
114 * modification, are permitted provided that the following conditions
115 * are met:
116 * * Redistributions of source code must retain the above copyright
117 * notice, this list of conditions and the following disclaimer.
118 * * Redistributions in binary form must reproduce the above copyright
119 * notice, this list of conditions and the following disclaimer in
120 * the documentation and/or other materials provided with the
121 * distribution.
122 *
123 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
124 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
125 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
126 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
127 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
128 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
129 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
130 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
131 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
132 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
133 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
134 */
135
136 #include <sys/cdefs.h>
137 __FBSDID("\$FreeBSD\$");
138
139 END_OF_NOTICE
140
141 if(!open(HDR, ">", "hsi_struct_decode.h")) {
142 print "Failure to open decoder output header file\n";
143 exit 1;
144 }
145
146 print HDR <<END_OF_NOTICE;
147 /*-
148 * BSD LICENSE
149 *
150 * Copyright(c) 2014-2015 Broadcom Corporation.
151 * All rights reserved.
152 *
153 * Redistribution and use in source and binary forms, with or without
154 * modification, are permitted provided that the following conditions
155 * are met:
156 *
157 * * Redistributions of source code must retain the above copyright
158 * notice, this list of conditions and the following disclaimer.
159 * * Redistributions in binary form must reproduce the above copyright
160 * notice, this list of conditions and the following disclaimer in
161 * the documentation and/or other materials provided with the
162 * distribution.
163 * * Neither the name of Broadcom Corporation nor the names of its
164 * contributors may be used to endorse or promote products derived
165 * from this software without specific prior written permission.
166 *
167 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
168 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
169 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
170 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
171 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
172 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
173 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
174 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
175 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
176 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
177 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
178 */
179
180 END_OF_NOTICE
181
182 print OUT "#ifdef HSI_DEBUG\n#include <inttypes.h>\n#include <rte_common.h>\n#include <rte_log.h>\n#include \"hsi_struct_def_dpdk.h\"\n#include \"hsi_struct_decode.h\"\n#include \"hsi_struct_decode.h\"\n\n";
183 print HDR "#ifdef HSI_DEBUG\n#include \"hsi_struct_def_dpdk.h\"\n\n";
184
185 my $hdr_defs = '';
186
187 sub print_single_val
188 {
189 my $field=shift;
190 my $type=shift;
191 my $max_field_len=shift;
192 my $name = shift;
193 my $macroshash = shift;
194 my %macros = %$macroshash;
195 $macrosref = shift;
196 my @macros = @$macrosref;
197 $macrosref = shift;
198 my @fields = @$macrosref;
199
200 if ($type eq 'uint32_t') {
201 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s = 0x%%08\"PRIX32\"\\n\", data->$field);\n",$max_field_len,$field;
202 }
203 elsif ($type eq 'uint16_t') {
204 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s = 0x%%04\"PRIX16\"\\n\", data->$field);\n",$max_field_len,$field;
205 }
206 elsif ($type eq 'uint8_t') {
207 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s = 0x%%02\"PRIX8\"\\n\", data->$field);\n",$max_field_len,$field;
208 }
209 elsif ($type eq 'uint64_t') {
210 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s = 0x%%016\"PRIX64\"\\n\", data->$field);\n",$max_field_len,$field;
211 }
212 elsif ($type eq 'char') {
213 if ($field =~ s/\[([0-9]+)\]//) {
214 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s = \\\"%%.$1s\\\"\\n\", data->$field);\n",$max_field_len,$field;
215 }
216 else {
217 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s = 0x%%02\"PRIX8\"\\n\", data->$field);\n",$max_field_len,$field;
218 }
219 }
220 else {
221 print "Unhandled type: '$type'\n";
222 }
223
224 my $macro_prefix = uc($name).'_'.uc($field).'_';
225 # Special handling for the common flags_type field
226 $macro_prefix =~ s/FLAGS_TYPE_$/FLAGS_/ if ($field eq 'flags_type');
227 # Special handling for _hi types
228 $macro_prefix =~ s/_HI_/_/ if ($name =~ /_hi$/);
229
230 $macro_prefix =~ s/\[[0-9]+\]//;
231 my %vmacros;
232 my $vmacros_have_mask = 0;
233 my @vmacros;
234 my %subfields;
235 my $all_single_bits=1;
236 MACRO:
237 foreach my $macro (@macros) {
238 if ($macro =~ /^$macro_prefix(.*)_MASK$/) {
239 my $macro = $&;
240 my $maskdef = $macros{$macro};
241 my $subfield = $1;
242 my $subfield_value = "(data->$field & $macro)";
243 if (defined $macros{"$macro_prefix$subfield\_SFT"}) {
244 $subfield_value = "($subfield_value >> $macro_prefix$subfield\_SFT)";
245 }
246 $maskdef =~ s/[x0 ]//g;
247 if ($type eq 'uint64_t') {
248 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s $subfield = %%0*\" PRIX64 \"\\n\", %u, $subfield_value);\n", $max_field_len, '', length($maskdef);
249 }
250 else {
251 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s $subfield = %%0*X\\n\", %u, $subfield_value);\n", $max_field_len, '', length($maskdef);
252 }
253 delete $$macroshash{$macro};
254 }
255 elsif ($macro =~ /^$macro_prefix(.*)_SFT$/) {
256 delete $$macroshash{$macro};
257 }
258 elsif ($macro =~ /^$macro_prefix\MASK$/) {
259 $vmacros_have_mask = 1;
260 delete $$macroshash{$macro};
261 }
262 elsif ($macro =~ /^$macro_prefix(.*)$/) {
263 my $macro = $&;
264 my $subfield = $1;
265
266 # Check for longer fields with the same base... ie: link and link_speed
267 foreach my $extra_field (@fields) {
268 next if ($extra_field eq $field);
269 if ($extra_field =~ /^$field/) {
270 my $extra_prefix = uc($name).'_'.uc($extra_field).'_';
271 next MACRO if ($macro =~ /^$extra_prefix/);
272 }
273 }
274
275 push @vmacros, $macro;
276 my $macroeval = $macros{$macro};
277 $macroeval =~ s/UINT32_C\((.*?)\)/$1/g;
278 $vmacros{$macro} = eval("$macroeval");
279 $subfields{$macro} = $subfield;
280
281 $all_single_bits = 0 if ($vmacros{$macro} & ($vmacros{$macro}-1));
282 $all_single_bits = 0 if ($vmacros{$macro} == 0);
283 }
284 }
285 if ($all_single_bits) {
286 foreach my $macro (@vmacros) {
287 my $subfield_value = "(data->$field & $macro)";
288 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s $subfields{$macro} : %%s\\n\", $subfield_value?\"ON\":\"OFF\");\n", $max_field_len, '';
289 delete $$macroshash{$macro};
290 }
291 }
292 else {
293 printf OUT "\tRTE_LOG(DEBUG, PMD, \" % *s Value : %%s\\n\",\n", $max_field_len, '';
294 foreach my $macro (@vmacros) {
295 my $subfield_value = "data->$field";
296 $subfield_value = "($subfield_value & $macro_prefix\MASK)" if $vmacros_have_mask;
297 print OUT "\t\t$subfield_value == $macro ? \"$subfields{$macro}\" :\n";
298 delete $$macroshash{$macro};
299 }
300 print OUT "\t\t\"Unknown\");\n";
301 }
302 }
303
304 while ($header =~ /^typedef\s+struct\s+(.*?)\s+{(.*?)^}/msg) {
305 my ($name,$def) = ($1, $2);
306 my @fields=();
307 my %type=();
308 my @macros=();
309 my %macros=();
310 my $max_field_len=0;
311
312 # First, pull out all the fields in order...
313 while($def =~ /^\s*([^\s#\/]+?)\s+([^;\/\s]+?)\s*;/mg) {
314 my ($type, $name) = ($1, $2);
315 push @fields, $name;
316 $type{$name}=$type;
317 $max_field_len = length($name) if length($name) > $max_field_len;
318 }
319 # Now, pull out the macros...
320 while($def =~ /^\s*\#define\s+([^\s]+?)\s+(.*?)\s*$/mg) {
321 push @macros, $1;
322 $macros{$1}=$2;
323 }
324
325 # Now, generate code to print the struct...
326 print OUT "void decode_$name(const char *string __rte_unused, struct $name *data) {\n\tRTE_LOG(DEBUG, PMD, \"$name\\n\");\n";
327 print HDR "void decode_$name(const char *string __rte_unused, struct $name *data);\n";
328 $hdr_defs .= "#define decode_$name(x, y) {}\n";
329 foreach my $field (@fields) {
330 if ($field =~ /\[([0-9]+)\]/) {
331 if ($type{$field} eq 'char') {
332 print_single_val($field, $type{$field}, $max_field_len, $name, \%macros, \@macros, \@fields);
333 }
334 else {
335 foreach my $idx (0..$1-1) {
336 my $item = $field;
337 $item =~ s/\[[0-9]+\]/[$idx]/;
338 print_single_val($item, $type{$field}, $max_field_len, $name, \%macros, \@macros, \@fields);
339 }
340 }
341 }
342 else {
343 print_single_val($field, $type{$field}, $max_field_len, $name, \%macros, \@macros, \@fields);
344 }
345 }
346 # print "Unhandled macros:\n",join("\n", keys %macros),"\n" if (keys %macros > 0);
347 print OUT "}\n\n";
348 }
349 print OUT "#endif\n";
350
351 print HDR "#else\n";
352 print HDR $hdr_defs;
353 print HDR "#endif\n";
354 close OUT;
355 close HDR;
356 }
Cache object: 46eefe91cce74adfb18f51ced09f4fd9
|