-
Notifications
You must be signed in to change notification settings - Fork 221
156 lines (140 loc) · 6.48 KB
/
check-code-style.yml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
# This workflow is intended to check if PR conforms with coding standards used
# in the project.
#
# Documentation for GitHub Actions:
# [workflow-syntax]: https://docs.github.com/en/free-pro-team@latest/actions/reference/workflow-syntax-for-github-actions
# [context-and-expression-syntax]: https://docs.github.com/en/free-pro-team@latest/actions/reference/context-and-expression-syntax-for-github-actions
# [workflow-commands]: https://docs.github.com/en/free-pro-team@latest/actions/reference/workflow-commands-for-github-actions
name: Check code style
on:
pull_request:
branches:
- main
- llvm_release_*
paths-ignore: # no need to check formatting for:
- 'docs/**' # documentation
- 'test/**' # tests
- '**.md' # README
- '**.txt' # CMakeLists.txt
- '**/check-**-build.yml' # Other workflows
env:
# We need compile command database in order to perform clang-tidy check. So,
# in order to perform configure step we need to setup llvm-dev package. This
# env variable used to specify desired version of it
LLVM_VERSION: 18
jobs:
clang-format-and-tidy:
name: clang-format & clang-tidy
runs-on: ubuntu-20.04
steps:
- name: Checkout sources
uses: actions/checkout@v3
with:
# In order to gather diff from PR we need to fetch not only the latest
# commit. Depth of 2 is enough, because GitHub Actions supply us with
# merge commit as {{ github.sha }}, i.e. the second commit is a merge
# base between target branch and PR
fetch-depth: 2
- name: Gather list of changes
id: gather-list-of-changes
run: |
git diff -U0 --no-color ${{ github.sha }}^ -- include lib \
':(exclude)include/LLVMSPIRVExtensions.inc' \
':(exclude)lib/SPIRV/libSPIRV/SPIRVErrorEnum.h' \
':(exclude)lib/SPIRV/libSPIRV/SPIRVOpCodeEnum.h' \
':(exclude)lib/SPIRV/libSPIRV/SPIRVOpCodeEnumInternal.h' \
> diff-to-inspect.txt
if [ -s diff-to-inspect.txt ]; then
# Here we set an output of our step, which is used later to either
# perform or skip further steps, i.e. there is no sense to install
# clang-format if PR hasn't changed .cpp files at all
# See [workflow-commands] for reference
echo '::set-output name=HAS_CHANGES::true'
fi
- name: Install dependencies
if: ${{ steps.gather-list-of-changes.outputs.HAS_CHANGES }}
run: |
# clang-tidy requires compile command database in order to be properly
# launched, so, we need to setup llvm package to perform cmake
# configuration step to generate that database
curl -L "https://apt.llvm.org/llvm-snapshot.gpg.key" | sudo apt-key add -
echo "deb https://apt.llvm.org/focal/ llvm-toolchain-focal main" | sudo tee -a /etc/apt/sources.list
sudo apt-get update
sudo apt-get install -yqq \
clang-format-${{ env.LLVM_VERSION }} clang-tidy-${{ env.LLVM_VERSION }} \
llvm-${{ env.LLVM_VERSION }}-dev libomp-${{ env.LLVM_VERSION }}-dev \
mlir-${{ env.LLVM_VERSION }}-tools \
- name: Generate compile command database
if: ${{ steps.gather-list-of-changes.outputs.HAS_CHANGES }}
run: |
mkdir build && cd build
cmake -DCMAKE_CXX_COMPILER=clang++-${{ env.LLVM_VERSION }} \
-DCMAKE_EXPORT_COMPILE_COMMANDS=ON -DCMAKE_BUILD_TYPE=Release -G "Unix Makefiles" ${{ github.workspace }}
- name: Run clang-format
if: ${{ steps.gather-list-of-changes.outputs.HAS_CHANGES }}
id: run-clang-format
run: |
cat diff-to-inspect.txt | /usr/share/clang/clang-format-${{ env.LLVM_VERSION }}/clang-format-diff.py \
-p1 -binary clang-format-${{ env.LLVM_VERSION }} > clang-format.patch
if [ -s clang-format.patch ]; then
echo "clang-format found incorrectly formatted code:"
cat clang-format.patch;
exit 1;
else
rm clang-format.patch # to avoid uploading empty file
fi
- name: Run clang-tidy
# By some reason, GitHub Actions automatically include "success()"
# expression into an "if" statement if it doesn't contain any of job
# status check functions. This is why this and following steps has
# "always()" and "failure()" in "if" conditions.
# See "Job status check functions" in [context-and-expression-syntax]
if: ${{ always() && steps.gather-list-of-changes.outputs.HAS_CHANGES }}
id: run-clang-tidy
run: |
cat diff-to-inspect.txt | /usr/lib/llvm-${{ env.LLVM_VERSION }}/share/clang/clang-tidy-diff.py \
-p1 -clang-tidy-binary clang-tidy-${{ env.LLVM_VERSION }} -quiet \
-path ${{ github.workspace}}/build > clang-tidy.log 2>/dev/null
# By some reason, clang-tidy log contains tons of extra empty lines,
# that confuse the check below
sed -i '/^$/d' clang-tidy.log
if [ -s clang-tidy.log ]; then
if ! grep -q "No relevant changes found." clang-tidy.log; then
# Emit annotations
while read -r line; do
type="error"
if [[ $line == *"warning:"* ]]; then
type="warning"
elif [[ $line == *"error:"* ]]; then
type="error"
else
continue
fi
absolute_path=$(echo $line | grep -Po "^[\w\d-./]+(?=:)")
relative_path=${absolute_path##"${{ github.workspace }}"}
line_number=$(echo $line | grep -Po "(?<=:)\d+(?=:\d)")
message=$(echo $line | grep -Po "(?<=${type}: ).*$")
# see [workflow-commands] for documentation
echo "::${type} file=${relative_path},line=${line_number}::${message}"
done < clang-tidy.log
echo "clang-tidy found incorrectly written code:"
cat clang-tidy.log
exit 1
else
rm clang-tidy.log # to avoid uploading empty file
fi
fi
- name: Upload patch with clang-format fixes
uses: actions/upload-artifact@v2
if: ${{ failure() && steps.run-clang-format.outcome == 'failure' }}
with:
name: clang-format.patch
path: clang-format.patch
if-no-files-found: ignore
- name: Upload clang-tidy log
uses: actions/upload-artifact@v2
if: ${{ failure() && steps.run-clang-tidy.outcome == 'failure' }}
with:
name: clang-tidy.log
path: clang-tidy.log
if-no-files-found: ignore