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