Merge branch 'jl/submodule-status-failure-report' into maint
[git] / t / valgrind / analyze.sh
1 #!/bin/sh
2
3 out_prefix=$(dirname "$0")/../test-results/valgrind.out
4 output=
5 count=0
6 total_count=0
7 missing_message=
8 new_line='
9 '
10
11 # start outputting the current valgrind error in $out_prefix.++$count,
12 # and the test case which failed in the corresponding .message file
13 start_output () {
14         test -z "$output" || return
15
16         # progress
17         total_count=$(($total_count+1))
18         test -t 2 && printf "\rFound %d errors" $total_count >&2
19
20         count=$(($count+1))
21         output=$out_prefix.$count
22         : > $output
23
24         echo "*** $1 ***" > $output.message
25 }
26
27 finish_output () {
28         test ! -z "$output" || return
29         output=
30
31         # if a test case has more than one valgrind error, we need to
32         # copy the last .message file to the previous errors
33         test -z "$missing_message" || {
34                 while test $missing_message -lt $count
35                 do
36                         cp $out_prefix.$count.message \
37                                 $out_prefix.$missing_message.message
38                         missing_message=$(($missing_message+1))
39                 done
40                 missing_message=
41         }
42 }
43
44 # group the valgrind errors by backtrace
45 output_all () {
46         last_line=
47         j=0
48         i=1
49         while test $i -le $count
50         do
51                 # output <number> <backtrace-in-one-line>
52                 echo "$i $(tr '\n' ' ' < $out_prefix.$i)"
53                 i=$(($i+1))
54         done |
55         sort -t ' ' -k 2 | # order by <backtrace-in-one-line>
56         while read number line
57         do
58                 # find duplicates, do not output backtrace twice
59                 if test "$line" != "$last_line"
60                 then
61                         last_line=$line
62                         j=$(($j+1))
63                         printf "\nValgrind error $j:\n\n"
64                         cat $out_prefix.$number
65                         printf "\nfound in:\n"
66                 fi
67                 # print the test case where this came from
68                 printf "\n"
69                 cat $out_prefix.$number.message
70         done
71 }
72
73 handle_one () {
74         OLDIFS=$IFS
75         IFS="$new_line"
76         while read line
77         do
78                 case "$line" in
79                 # backtrace, possibly a new one
80                 ==[0-9]*)
81
82                         # Does the current valgrind error have a message yet?
83                         case "$output" in
84                         *.message)
85                                 test -z "$missing_message" &&
86                                 missing_message=$count
87                                 output=
88                         esac
89
90                         start_output $(basename $1)
91                         echo "$line" |
92                         sed 's/==[0-9]*==/==valgrind==/' >> $output
93                         ;;
94                 # end of backtrace
95                 '}')
96                         test -z "$output" || {
97                                 echo "$line" >> $output
98                                 test $output = ${output%.message} &&
99                                 output=$output.message
100                         }
101                         ;;
102                 # end of test case
103                 '')
104                         finish_output
105                         ;;
106                 # normal line; if $output is set, print the line
107                 *)
108                         test -z "$output" || echo "$line" >> $output
109                         ;;
110                 esac
111         done < $1
112         IFS=$OLDIFS
113
114         # just to be safe
115         finish_output
116 }
117
118 for test_script in "$(dirname "$0")"/../test-results/*.out
119 do
120         handle_one $test_script
121 done
122
123 output_all