9 if (!defined($warns)) {
10 print "usage: $0 <warns.txt>\n";
14 my $db = DBI
->connect("dbi:SQLite:smatch_db.sqlite", "", "", {AutoCommit
=> 0});
15 $db->do("PRAGMA synchronous = OFF");
16 $db->do("PRAGMA cache_size = 800000");
17 $db->do("PRAGMA journal_mode = OFF");
19 $db->do("delete from return_implies");
21 my $type = 7; # RANGE_CAP
28 if ($str =~ /^\((.*)\)/) {
38 if ($str =~ /^\((.*)\)/) {
59 if ($min =~ /^$max$/) {
65 sub get_error_returns
($)
67 my $total_ranges = shift;
71 foreach my $range (split(",", $total_ranges)) {
72 my ($range_1, $range_2);
75 if ($range =~ /(.*[^(])-(.*)/) {
83 $min = get_error_num
($range_1);
84 $max = get_error_num
($range_2);
87 push @error_ranges, $range;
88 } elsif ($min + 0 < 0) {
89 push @error_ranges, show_num
($min) . "-(-1)";
93 foreach my $range (@error_ranges) {
102 sub get_success_returns
($)
104 my $total_ranges = shift;
108 foreach my $range (split(",", $total_ranges)) {
109 my ($range_1, $range_2);
112 if ($range =~ /(.*[^(])-(.*)/) {
120 $min = get_error_num
($range_1);
121 $max = get_error_num
($range_2);
124 push @success_ranges, $range;
125 } elsif ($max + 0 >= 0 || $max =~ /max/) {
126 push @success_ranges, show_range
(0, $range_2);
130 foreach my $range (@success_ranges) {
134 $ret = $ret . $range;
145 foreach my $range (split(",", $orig)) {
146 my ($range_1, $range_2);
149 if ($range =~ /(.*[^(])-(.*)/) {
157 $min = get_num
($range_1);
158 $min = show_num
($min - 1);
160 $max = get_num
($range_2);
161 $max = show_num
($max + 1);
163 if (!defined($old_max)) {
164 if (!($range_1 =~ /min/)) {
165 $ret = "min-" . $min;
172 $ret = $ret . show_range
($old_max, $min);
177 if (!($orig =~ /max$/)) {
181 $ret = $ret . "$old_max-max";
188 my $total_returns = "";
190 open(FILE
, "<$warns");
192 # test.c:26 func() info: function_return_values '(-20),(-12),0' global
193 if (/.*?:\d+ (\w+)\(\) info: function_return_values '(.*?)'/) {
198 # test.c:14 func() info: param 0 range 'min-(-1),12-max' implies error return static
199 if (/(.*?):\d+ (\w+)\(\) info: param (\d+) range '(.*?)' implies error return (global|static)/) {
206 if ($5 =~ /static/) {
212 my $good_range = invert_range
($bad_range);
214 if (!($func =~ /^$old_func$/)) {
218 $error_returns = get_error_returns
($total_returns);
219 $success_returns = get_success_returns
($total_returns);
221 $db->do("insert into return_implies values ('$file', '$func', $static, $type, '$success_returns', $param, '', '$good_range')");
222 $db->do("insert into return_implies values ('$file', '$func', $static, $type, '$error_returns', $param, '', 'min-max')");
228 open(FILE
, "<$warns");
230 # crypto/cbc.c:54 is_power_of_2() info: bool_return_implication "1" 0 "min-(-1),1-max static"
231 if (/(.*?):\d+ (\w+)\(\) info: bool_return_implication "(.*?)" (\d+) "(.*?)" (global|static)/) {
234 my $return_range = $3;
236 my $implied_range = $5;
238 if ($6 =~ /static/) {
242 $db->do("insert into return_implies values ('$file', '$func', $static, $type, '$return_range', $param, '', '$implied_range')");