xref: /freebsd/sys/contrib/openzfs/scripts/commitcheck.sh (revision 546d3d08e5993cbe2d6141b256e8c2ebad5aa102)
1#!/bin/sh
2
3REF="HEAD"
4
5# test commit body for length
6# lines containing urls are exempt for the length limit.
7test_commit_bodylength()
8{
9    length="72"
10    body=$(git log --no-show-signature -n 1 --pretty=%b "$REF" |
11        grep -Evi -e "http(s)*://" -e "signed-off-by:" -e "reviewed-by:" |
12        grep -E -m 1 ".{$((length + 1))}")
13    if [ -n "$body" ]; then
14        echo "error: commit message body contains line over ${length} characters"
15        return 1
16    fi
17
18    return 0
19}
20
21# check for a tagged line
22check_tagged_line()
23{
24    regex='^[[:space:]]*'"$1"':[[:space:]][[:print:]]+[[:space:]]<[[:graph:]]+>$'
25    foundline=$(git log --no-show-signature -n 1 "$REF" | grep -E -m 1 "$regex")
26    if [ -z "$foundline" ]; then
27        echo "error: missing \"$1\""
28        return 1
29    fi
30
31    return 0
32}
33
34# check commit message for a normal commit
35new_change_commit()
36{
37    error=0
38
39    # subject is not longer than 72 characters
40    long_subject=$(git log --no-show-signature -n 1 --pretty=%s "$REF" | grep -E -m 1 '.{73}')
41    if [ -n "$long_subject" ]; then
42        echo "error: commit subject over 72 characters"
43        error=1
44    fi
45
46    # need a signed off by
47    if ! check_tagged_line "Signed-off-by" ; then
48        error=1
49    fi
50
51    # ensure that no lines in the body of the commit are over 72 characters
52    if ! test_commit_bodylength ; then
53        error=1
54    fi
55
56    return "$error"
57}
58
59is_coverity_fix()
60{
61    # subject starts with Fix coverity defects means it's a coverity fix
62    subject=$(git log --no-show-signature -n 1 --pretty=%s "$REF" | grep -E -m 1 '^Fix coverity defects')
63    if [ -n "$subject" ]; then
64        return 0
65    fi
66
67    return 1
68}
69
70coverity_fix_commit()
71{
72    error=0
73
74    # subject starts with Fix coverity defects: CID dddd, dddd...
75    subject=$(git log --no-show-signature -n 1 --pretty=%s "$REF" |
76        grep -E -m 1 'Fix coverity defects: CID [[:digit:]]+(, [[:digit:]]+)*')
77    if [ -z "$subject" ]; then
78        echo "error: Coverity defect fixes must have a subject line that starts with \"Fix coverity defects: CID dddd\""
79        error=1
80    fi
81
82    # need a signed off by
83    if ! check_tagged_line "Signed-off-by" ; then
84        error=1
85    fi
86
87    # test each summary line for the proper format
88    OLDIFS=$IFS
89    IFS='
90'
91    for line in $(git log --no-show-signature -n 1 --pretty=%b "$REF" | grep -E '^CID'); do
92        if ! echo "$line" | grep -qE '^CID [[:digit:]]+: ([[:graph:]]+|[[:space:]])+ \(([[:upper:]]|\_)+\)'; then
93            echo "error: commit message has an improperly formatted CID defect line"
94            error=1
95        fi
96    done
97    IFS=$OLDIFS
98
99    # ensure that no lines in the body of the commit are over 72 characters
100    if ! test_commit_bodylength; then
101        error=1
102    fi
103
104    return "$error"
105}
106
107if [ -n "$1" ]; then
108    REF="$1"
109fi
110
111# if coverity fix, test against that
112if is_coverity_fix; then
113    if ! coverity_fix_commit; then
114        exit 1
115    else
116        exit 0
117    fi
118fi
119
120# have a normal commit
121if ! new_change_commit ; then
122    exit 1
123fi
124
125exit 0
126