mkerr.pl 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715
  1. #!/usr/local/bin/perl -w
  2. my $config = "crypto/err/openssl.ec";
  3. my $debug = 0;
  4. my $rebuild = 0;
  5. my $static = 1;
  6. my $recurse = 0;
  7. my $reindex = 0;
  8. my $dowrite = 0;
  9. my $staticloader = "";
  10. my $pack_errcode;
  11. my $load_errcode;
  12. while (@ARGV) {
  13. my $arg = $ARGV[0];
  14. if($arg eq "-conf") {
  15. shift @ARGV;
  16. $config = shift @ARGV;
  17. } elsif($arg eq "-debug") {
  18. $debug = 1;
  19. shift @ARGV;
  20. } elsif($arg eq "-rebuild") {
  21. $rebuild = 1;
  22. shift @ARGV;
  23. } elsif($arg eq "-recurse") {
  24. $recurse = 1;
  25. shift @ARGV;
  26. } elsif($arg eq "-reindex") {
  27. $reindex = 1;
  28. shift @ARGV;
  29. } elsif($arg eq "-nostatic") {
  30. $static = 0;
  31. shift @ARGV;
  32. } elsif($arg eq "-staticloader") {
  33. $staticloader = "static ";
  34. shift @ARGV;
  35. } elsif($arg eq "-write") {
  36. $dowrite = 1;
  37. shift @ARGV;
  38. } else {
  39. last;
  40. }
  41. }
  42. if($recurse) {
  43. @source = ( <crypto/*.c>, <crypto/*/*.c>, <ssl/*.c>,
  44. <fips/*.c>, <fips/*/*.c>);
  45. } else {
  46. @source = @ARGV;
  47. }
  48. # Read in the config file
  49. open(IN, "<$config") || die "Can't open config file $config";
  50. # Parse config file
  51. while(<IN>)
  52. {
  53. if(/^L\s+(\S+)\s+(\S+)\s+(\S+)/) {
  54. $hinc{$1} = $2;
  55. $libinc{$2} = $1;
  56. $cskip{$3} = $1;
  57. if($3 ne "NONE") {
  58. $csrc{$1} = $3;
  59. $fmax{$1} = 99;
  60. $rmax{$1} = 99;
  61. $fassigned{$1} = ":";
  62. $rassigned{$1} = ":";
  63. $fnew{$1} = 0;
  64. $rnew{$1} = 0;
  65. }
  66. } elsif (/^F\s+(\S+)/) {
  67. # Add extra function with $1
  68. } elsif (/^R\s+(\S+)\s+(\S+)/) {
  69. $rextra{$1} = $2;
  70. $rcodes{$1} = $2;
  71. }
  72. }
  73. close IN;
  74. # Scan each header file in turn and make a list of error codes
  75. # and function names
  76. while (($hdr, $lib) = each %libinc)
  77. {
  78. next if($hdr eq "NONE");
  79. print STDERR "Scanning header file $hdr\n" if $debug;
  80. my $line = "", $def= "", $linenr = 0, $gotfile = 0;
  81. if (open(IN, "<$hdr")) {
  82. $gotfile = 1;
  83. while(<IN>) {
  84. $linenr++;
  85. print STDERR "line: $linenr\r" if $debug;
  86. last if(/BEGIN\s+ERROR\s+CODES/);
  87. if ($line ne '') {
  88. $_ = $line . $_;
  89. $line = '';
  90. }
  91. if (/\\$/) {
  92. $line = $_;
  93. next;
  94. }
  95. if(/\/\*/) {
  96. if (not /\*\//) { # multiline comment...
  97. $line = $_; # ... just accumulate
  98. next;
  99. } else {
  100. s/\/\*.*?\*\///gs; # wipe it
  101. }
  102. }
  103. if ($cpp) {
  104. $cpp++ if /^#\s*if/;
  105. $cpp-- if /^#\s*endif/;
  106. next;
  107. }
  108. $cpp = 1 if /^#.*ifdef.*cplusplus/; # skip "C" declaration
  109. next if (/^\#/); # skip preprocessor directives
  110. s/{[^{}]*}//gs; # ignore {} blocks
  111. if (/\{|\/\*/) { # Add a } so editor works...
  112. $line = $_;
  113. } else {
  114. $def .= $_;
  115. }
  116. }
  117. }
  118. print STDERR " \r" if $debug;
  119. $defnr = 0;
  120. # Delete any DECLARE_ macros
  121. $def =~ s/DECLARE_\w+\([\w,\s]+\)//gs;
  122. foreach (split /;/, $def) {
  123. $defnr++;
  124. print STDERR "def: $defnr\r" if $debug;
  125. # The goal is to collect function names from function declarations.
  126. s/^[\n\s]*//g;
  127. s/[\n\s]*$//g;
  128. # Skip over recognized non-function declarations
  129. next if(/typedef\W/ or /DECLARE_STACK_OF/ or /TYPEDEF_.*_OF/);
  130. # Remove STACK_OF(foo)
  131. s/STACK_OF\(\w+\)/void/;
  132. # Reduce argument lists to empty ()
  133. # fold round brackets recursively: (t(*v)(t),t) -> (t{}{},t) -> {}
  134. while(/\(.*\)/s) {
  135. s/\([^\(\)]+\)/\{\}/gs;
  136. s/\(\s*\*\s*(\w+)\s*\{\}\s*\)/$1/gs; #(*f{}) -> f
  137. }
  138. # pretend as we didn't use curly braces: {} -> ()
  139. s/\{\}/\(\)/gs;
  140. if (/(\w+)\s*\(\).*/s) { # first token prior [first] () is
  141. my $name = $1; # a function name!
  142. $name =~ tr/[a-z]/[A-Z]/;
  143. $ftrans{$name} = $1;
  144. } elsif (/[\(\)]/ and not (/=/)) {
  145. print STDERR "Header $hdr: cannot parse: $_;\n";
  146. }
  147. }
  148. print STDERR " \r" if $debug;
  149. next if $reindex;
  150. # Scan function and reason codes and store them: keep a note of the
  151. # maximum code used.
  152. if ($gotfile) {
  153. while(<IN>) {
  154. if(/^\#\s*define\s+(\S+)\s+(\S+)/) {
  155. $name = $1;
  156. $code = $2;
  157. next if $name =~ /^${lib}err/;
  158. unless($name =~ /^${lib}_([RF])_(\w+)$/) {
  159. print STDERR "Invalid error code $name\n";
  160. next;
  161. }
  162. if($1 eq "R") {
  163. $rcodes{$name} = $code;
  164. if ($rassigned{$lib} =~ /:$code:/) {
  165. print STDERR "!! ERROR: $lib reason code $code assigned twice\n";
  166. }
  167. $rassigned{$lib} .= "$code:";
  168. if(!(exists $rextra{$name}) &&
  169. ($code > $rmax{$lib}) ) {
  170. $rmax{$lib} = $code;
  171. }
  172. } else {
  173. if ($fassigned{$lib} =~ /:$code:/) {
  174. print STDERR "!! ERROR: $lib function code $code assigned twice\n";
  175. }
  176. $fassigned{$lib} .= "$code:";
  177. if($code > $fmax{$lib}) {
  178. $fmax{$lib} = $code;
  179. }
  180. $fcodes{$name} = $code;
  181. }
  182. }
  183. }
  184. }
  185. if ($debug) {
  186. if (defined($fmax{$lib})) {
  187. print STDERR "Max function code fmax" . "{" . "$lib" . "} = $fmax{$lib}\n";
  188. $fassigned{$lib} =~ m/^:(.*):$/;
  189. @fassigned = sort {$a <=> $b} split(":", $1);
  190. print STDERR " @fassigned\n";
  191. }
  192. if (defined($rmax{$lib})) {
  193. print STDERR "Max reason code rmax" . "{" . "$lib" . "} = $rmax{$lib}\n";
  194. $rassigned{$lib} =~ m/^:(.*):$/;
  195. @rassigned = sort {$a <=> $b} split(":", $1);
  196. print STDERR " @rassigned\n";
  197. }
  198. }
  199. if ($lib eq "SSL") {
  200. if ($rmax{$lib} >= 1000) {
  201. print STDERR "!! ERROR: SSL error codes 1000+ are reserved for alerts.\n";
  202. print STDERR "!! Any new alerts must be added to $config.\n";
  203. print STDERR "\n";
  204. }
  205. }
  206. close IN;
  207. }
  208. # Scan each C source file and look for function and reason codes
  209. # This is done by looking for strings that "look like" function or
  210. # reason codes: basically anything consisting of all upper case and
  211. # numerics which has _F_ or _R_ in it and which has the name of an
  212. # error library at the start. This seems to work fine except for the
  213. # oddly named structure BIO_F_CTX which needs to be ignored.
  214. # If a code doesn't exist in list compiled from headers then mark it
  215. # with the value "X" as a place holder to give it a value later.
  216. # Store all function and reason codes found in %ufcodes and %urcodes
  217. # so all those unreferenced can be printed out.
  218. foreach $file (@source) {
  219. # Don't parse the error source file.
  220. next if exists $cskip{$file};
  221. print STDERR "File loaded: ".$file."\r" if $debug;
  222. open(IN, "<$file") || die "Can't open source file $file\n";
  223. while(<IN>) {
  224. if(/(([A-Z0-9]+)_F_([A-Z0-9_]+))/) {
  225. next unless exists $csrc{$2};
  226. next if($1 eq "BIO_F_BUFFER_CTX");
  227. $ufcodes{$1} = 1;
  228. if(!exists $fcodes{$1}) {
  229. $fcodes{$1} = "X";
  230. $fnew{$2}++;
  231. }
  232. $notrans{$1} = 1 unless exists $ftrans{$3};
  233. }
  234. if(/(([A-Z0-9]+)_R_[A-Z0-9_]+)/) {
  235. next unless exists $csrc{$2};
  236. $urcodes{$1} = 1;
  237. if(!exists $rcodes{$1}) {
  238. $rcodes{$1} = "X";
  239. $rnew{$2}++;
  240. }
  241. }
  242. }
  243. close IN;
  244. }
  245. print STDERR " \n" if $debug;
  246. # Now process each library in turn.
  247. foreach $lib (keys %csrc)
  248. {
  249. my $hfile = $hinc{$lib};
  250. my $cfile = $csrc{$lib};
  251. if(!$fnew{$lib} && !$rnew{$lib}) {
  252. print STDERR "$lib:\t\tNo new error codes\n";
  253. next unless $rebuild;
  254. } else {
  255. print STDERR "$lib:\t\t$fnew{$lib} New Functions,";
  256. print STDERR " $rnew{$lib} New Reasons.\n";
  257. next unless $dowrite;
  258. }
  259. # If we get here then we have some new error codes so we
  260. # need to rebuild the header file and C file.
  261. # Make a sorted list of error and reason codes for later use.
  262. my @function = sort grep(/^${lib}_/,keys %fcodes);
  263. my @reasons = sort grep(/^${lib}_/,keys %rcodes);
  264. # Rewrite the header file
  265. if (open(IN, "<$hfile")) {
  266. # Copy across the old file
  267. while(<IN>) {
  268. push @out, $_;
  269. last if (/BEGIN ERROR CODES/);
  270. }
  271. close IN;
  272. } else {
  273. push @out,
  274. "/* ====================================================================\n",
  275. " * Copyright (c) 2001-2011 The OpenSSL Project. All rights reserved.\n",
  276. " *\n",
  277. " * Redistribution and use in source and binary forms, with or without\n",
  278. " * modification, are permitted provided that the following conditions\n",
  279. " * are met:\n",
  280. " *\n",
  281. " * 1. Redistributions of source code must retain the above copyright\n",
  282. " * notice, this list of conditions and the following disclaimer. \n",
  283. " *\n",
  284. " * 2. Redistributions in binary form must reproduce the above copyright\n",
  285. " * notice, this list of conditions and the following disclaimer in\n",
  286. " * the documentation and/or other materials provided with the\n",
  287. " * distribution.\n",
  288. " *\n",
  289. " * 3. All advertising materials mentioning features or use of this\n",
  290. " * software must display the following acknowledgment:\n",
  291. " * \"This product includes software developed by the OpenSSL Project\n",
  292. " * for use in the OpenSSL Toolkit. (http://www.openssl.org/)\"\n",
  293. " *\n",
  294. " * 4. The names \"OpenSSL Toolkit\" and \"OpenSSL Project\" must not be used to\n",
  295. " * endorse or promote products derived from this software without\n",
  296. " * prior written permission. For written permission, please contact\n",
  297. " * openssl-core\@openssl.org.\n",
  298. " *\n",
  299. " * 5. Products derived from this software may not be called \"OpenSSL\"\n",
  300. " * nor may \"OpenSSL\" appear in their names without prior written\n",
  301. " * permission of the OpenSSL Project.\n",
  302. " *\n",
  303. " * 6. Redistributions of any form whatsoever must retain the following\n",
  304. " * acknowledgment:\n",
  305. " * \"This product includes software developed by the OpenSSL Project\n",
  306. " * for use in the OpenSSL Toolkit (http://www.openssl.org/)\"\n",
  307. " *\n",
  308. " * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY\n",
  309. " * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE\n",
  310. " * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR\n",
  311. " * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR\n",
  312. " * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\n",
  313. " * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT\n",
  314. " * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n",
  315. " * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)\n",
  316. " * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,\n",
  317. " * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)\n",
  318. " * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED\n",
  319. " * OF THE POSSIBILITY OF SUCH DAMAGE.\n",
  320. " * ====================================================================\n",
  321. " *\n",
  322. " * This product includes cryptographic software written by Eric Young\n",
  323. " * (eay\@cryptsoft.com). This product includes software written by Tim\n",
  324. " * Hudson (tjh\@cryptsoft.com).\n",
  325. " *\n",
  326. " */\n",
  327. "\n",
  328. "#ifndef HEADER_${lib}_ERR_H\n",
  329. "#define HEADER_${lib}_ERR_H\n",
  330. "\n",
  331. "/* BEGIN ERROR CODES */\n";
  332. }
  333. open (OUT, ">$hfile") || die "Can't Open File $hfile for writing\n";
  334. print OUT @out;
  335. undef @out;
  336. print OUT <<"EOF";
  337. /*
  338. * The following lines are auto generated by the script mkerr.pl. Any changes
  339. * made after this point may be overwritten when the script is next run.
  340. */
  341. EOF
  342. if($static) {
  343. print OUT <<"EOF";
  344. ${staticloader}void ERR_load_${lib}_strings(void);
  345. EOF
  346. } else {
  347. print OUT <<"EOF";
  348. ${staticloader}void ERR_load_${lib}_strings(void);
  349. ${staticloader}void ERR_unload_${lib}_strings(void);
  350. ${staticloader}void ERR_${lib}_error(int function, int reason, char *file, int line);
  351. # define ${lib}err(f,r) ERR_${lib}_error((f),(r),__FILE__,__LINE__)
  352. EOF
  353. }
  354. print OUT <<"EOF";
  355. /* Error codes for the $lib functions. */
  356. /* Function codes. */
  357. EOF
  358. foreach $i (@function) {
  359. $z=48 - length($i);
  360. if($fcodes{$i} eq "X") {
  361. $fassigned{$lib} =~ m/^:([^:]*):/;
  362. $findcode = $1;
  363. if (!defined($findcode)) {
  364. $findcode = $fmax{$lib};
  365. }
  366. while ($fassigned{$lib} =~ m/:$findcode:/) {
  367. $findcode++;
  368. }
  369. $fcodes{$i} = $findcode;
  370. $fassigned{$lib} .= "$findcode:";
  371. print STDERR "New Function code $i\n" if $debug;
  372. }
  373. printf OUT "# define $i%s $fcodes{$i}\n"," " x $z;
  374. }
  375. print OUT "\n/* Reason codes. */\n";
  376. foreach $i (@reasons) {
  377. $z=48 - length($i);
  378. if($rcodes{$i} eq "X") {
  379. $rassigned{$lib} =~ m/^:([^:]*):/;
  380. $findcode = $1;
  381. if (!defined($findcode)) {
  382. $findcode = $rmax{$lib};
  383. }
  384. while ($rassigned{$lib} =~ m/:$findcode:/) {
  385. $findcode++;
  386. }
  387. $rcodes{$i} = $findcode;
  388. $rassigned{$lib} .= "$findcode:";
  389. print STDERR "New Reason code $i\n" if $debug;
  390. }
  391. printf OUT "# define $i%s $rcodes{$i}\n"," " x $z;
  392. }
  393. print OUT <<"EOF";
  394. #ifdef __cplusplus
  395. }
  396. #endif
  397. #endif
  398. EOF
  399. close OUT;
  400. # Rewrite the C source file containing the error details.
  401. # First, read any existing reason string definitions:
  402. my %err_reason_strings;
  403. if (open(IN,"<$cfile")) {
  404. while (<IN>) {
  405. if (/\b(${lib}_R_\w*)\b.*\"(.*)\"/) {
  406. $err_reason_strings{$1} = $2;
  407. }
  408. }
  409. close(IN);
  410. }
  411. my $hincf;
  412. if($static) {
  413. $hfile =~ /([^\/]+)$/;
  414. $hincf = "<openssl/$1>";
  415. } else {
  416. $hincf = "\"$hfile\"";
  417. }
  418. # If static we know the error code at compile time so use it
  419. # in error definitions.
  420. if ($static)
  421. {
  422. $pack_errcode = "ERR_LIB_${lib}";
  423. $load_errcode = "0";
  424. }
  425. else
  426. {
  427. $pack_errcode = "0";
  428. $load_errcode = "ERR_LIB_${lib}";
  429. }
  430. open (OUT,">$cfile") || die "Can't open $cfile for writing";
  431. print OUT <<"EOF";
  432. /* $cfile */
  433. /* ====================================================================
  434. * Copyright (c) 1999-2011 The OpenSSL Project. All rights reserved.
  435. *
  436. * Redistribution and use in source and binary forms, with or without
  437. * modification, are permitted provided that the following conditions
  438. * are met:
  439. *
  440. * 1. Redistributions of source code must retain the above copyright
  441. * notice, this list of conditions and the following disclaimer.
  442. *
  443. * 2. Redistributions in binary form must reproduce the above copyright
  444. * notice, this list of conditions and the following disclaimer in
  445. * the documentation and/or other materials provided with the
  446. * distribution.
  447. *
  448. * 3. All advertising materials mentioning features or use of this
  449. * software must display the following acknowledgment:
  450. * "This product includes software developed by the OpenSSL Project
  451. * for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
  452. *
  453. * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
  454. * endorse or promote products derived from this software without
  455. * prior written permission. For written permission, please contact
  456. * openssl-core\@OpenSSL.org.
  457. *
  458. * 5. Products derived from this software may not be called "OpenSSL"
  459. * nor may "OpenSSL" appear in their names without prior written
  460. * permission of the OpenSSL Project.
  461. *
  462. * 6. Redistributions of any form whatsoever must retain the following
  463. * acknowledgment:
  464. * "This product includes software developed by the OpenSSL Project
  465. * for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
  466. *
  467. * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
  468. * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  469. * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
  470. * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR
  471. * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  472. * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
  473. * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  474. * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  475. * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
  476. * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
  477. * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
  478. * OF THE POSSIBILITY OF SUCH DAMAGE.
  479. * ====================================================================
  480. *
  481. * This product includes cryptographic software written by Eric Young
  482. * (eay\@cryptsoft.com). This product includes software written by Tim
  483. * Hudson (tjh\@cryptsoft.com).
  484. *
  485. */
  486. /*
  487. * NOTE: this file was auto generated by the mkerr.pl script: any changes
  488. * made to it will be overwritten when the script next updates this file,
  489. * only reason strings will be preserved.
  490. */
  491. #include <stdio.h>
  492. #include <openssl/err.h>
  493. #include $hincf
  494. /* BEGIN ERROR CODES */
  495. #ifndef OPENSSL_NO_ERR
  496. # define ERR_FUNC(func) ERR_PACK($pack_errcode,func,0)
  497. # define ERR_REASON(reason) ERR_PACK($pack_errcode,0,reason)
  498. static ERR_STRING_DATA ${lib}_str_functs[] = {
  499. EOF
  500. # Add each function code: if a function name is found then use it.
  501. foreach $i (@function) {
  502. my $fn;
  503. $i =~ /^${lib}_F_(\S+)$/;
  504. $fn = $1;
  505. if(exists $ftrans{$fn}) {
  506. $fn = $ftrans{$fn};
  507. }
  508. # print OUT "{ERR_PACK($pack_errcode,$i,0),\t\"$fn\"},\n";
  509. if(length($i) + length($fn) > 58) {
  510. print OUT " {ERR_FUNC($i),\n \"$fn\"},\n";
  511. } else {
  512. print OUT " {ERR_FUNC($i), \"$fn\"},\n";
  513. }
  514. }
  515. print OUT <<"EOF";
  516. {0, NULL}
  517. };
  518. static ERR_STRING_DATA ${lib}_str_reasons[] = {
  519. EOF
  520. # Add each reason code.
  521. foreach $i (@reasons) {
  522. my $rn;
  523. my $rstr = "ERR_REASON($i)";
  524. if (exists $err_reason_strings{$i}) {
  525. $rn = $err_reason_strings{$i};
  526. } else {
  527. $i =~ /^${lib}_R_(\S+)$/;
  528. $rn = $1;
  529. $rn =~ tr/_[A-Z]/ [a-z]/;
  530. }
  531. if(length($i) + length($rn) > 56) {
  532. print OUT " {${rstr},\n \"$rn\"},\n";
  533. } else {
  534. print OUT " {${rstr}, \"$rn\"},\n";
  535. }
  536. }
  537. if($static) {
  538. print OUT <<"EOF";
  539. {0, NULL}
  540. };
  541. #endif
  542. ${staticloader}void ERR_load_${lib}_strings(void)
  543. {
  544. #ifndef OPENSSL_NO_ERR
  545. if (ERR_func_error_string(${lib}_str_functs[0].error) == NULL) {
  546. ERR_load_strings($load_errcode, ${lib}_str_functs);
  547. ERR_load_strings($load_errcode, ${lib}_str_reasons);
  548. }
  549. #endif
  550. }
  551. EOF
  552. } else {
  553. print OUT <<"EOF";
  554. {0, NULL}
  555. };
  556. #endif
  557. #ifdef ${lib}_LIB_NAME
  558. static ERR_STRING_DATA ${lib}_lib_name[] = {
  559. {0, ${lib}_LIB_NAME},
  560. {0, NULL}
  561. };
  562. #endif
  563. static int ${lib}_lib_error_code = 0;
  564. static int ${lib}_error_init = 1;
  565. ${staticloader}void ERR_load_${lib}_strings(void)
  566. {
  567. if (${lib}_lib_error_code == 0)
  568. ${lib}_lib_error_code = ERR_get_next_error_library();
  569. if (${lib}_error_init) {
  570. ${lib}_error_init = 0;
  571. #ifndef OPENSSL_NO_ERR
  572. ERR_load_strings(${lib}_lib_error_code, ${lib}_str_functs);
  573. ERR_load_strings(${lib}_lib_error_code, ${lib}_str_reasons);
  574. #endif
  575. #ifdef ${lib}_LIB_NAME
  576. ${lib}_lib_name->error = ERR_PACK(${lib}_lib_error_code, 0, 0);
  577. ERR_load_strings(0, ${lib}_lib_name);
  578. #endif
  579. }
  580. }
  581. ${staticloader}void ERR_unload_${lib}_strings(void)
  582. {
  583. if (${lib}_error_init == 0) {
  584. #ifndef OPENSSL_NO_ERR
  585. ERR_unload_strings(${lib}_lib_error_code, ${lib}_str_functs);
  586. ERR_unload_strings(${lib}_lib_error_code, ${lib}_str_reasons);
  587. #endif
  588. #ifdef ${lib}_LIB_NAME
  589. ERR_unload_strings(0, ${lib}_lib_name);
  590. #endif
  591. ${lib}_error_init = 1;
  592. }
  593. }
  594. ${staticloader}void ERR_${lib}_error(int function, int reason, char *file, int line)
  595. {
  596. if (${lib}_lib_error_code == 0)
  597. ${lib}_lib_error_code = ERR_get_next_error_library();
  598. ERR_PUT_error(${lib}_lib_error_code, function, reason, file, line);
  599. }
  600. EOF
  601. }
  602. close OUT;
  603. undef %err_reason_strings;
  604. }
  605. if($debug && %notrans) {
  606. print STDERR "The following function codes were not translated:\n";
  607. foreach(sort keys %notrans)
  608. {
  609. print STDERR "$_\n";
  610. }
  611. }
  612. # Make a list of unreferenced function and reason codes
  613. foreach (keys %fcodes) {
  614. push (@funref, $_) unless exists $ufcodes{$_};
  615. }
  616. foreach (keys %rcodes) {
  617. push (@runref, $_) unless exists $urcodes{$_};
  618. }
  619. if($debug && @funref) {
  620. print STDERR "The following function codes were not referenced:\n";
  621. foreach(sort @funref)
  622. {
  623. print STDERR "$_\n";
  624. }
  625. }
  626. if($debug && @runref) {
  627. print STDERR "The following reason codes were not referenced:\n";
  628. foreach(sort @runref)
  629. {
  630. print STDERR "$_\n";
  631. }
  632. }