246 lines
10 KiB
YAML
246 lines
10 KiB
YAML
![]() |
name: check Workflow
|
|||
|
|
|||
|
on:
|
|||
|
workflow_call:
|
|||
|
inputs:
|
|||
|
image_name:
|
|||
|
required: true
|
|||
|
type: string
|
|||
|
default: ubuntu
|
|||
|
image_tag:
|
|||
|
required: false
|
|||
|
type: string
|
|||
|
default: latest
|
|||
|
|
|||
|
jobs:
|
|||
|
check:
|
|||
|
runs-on: amd64
|
|||
|
container:
|
|||
|
image: ${{ inputs.image_name }}:${{ inputs.image_tag }}
|
|||
|
steps:
|
|||
|
- name: Checkout code
|
|||
|
uses: actions/checkout@v4
|
|||
|
env:
|
|||
|
https_proxy: ${{ secrets.https_proxy }}
|
|||
|
http_proxy: ${{ secrets.http_proxy }}
|
|||
|
with:
|
|||
|
ref: ${{ github.event.pull_request.head.sha }}
|
|||
|
|
|||
|
|
|||
|
- name: Get short sha
|
|||
|
id: slug
|
|||
|
run: echo "sha8=$(echo ${GITHUB_SHA} | cut -c1-8)" >> $GITHUB_OUTPUT
|
|||
|
|
|||
|
- name: generate cppcheck.sh
|
|||
|
run: |
|
|||
|
echo "generate /tmp/cppcheck.sh ..."
|
|||
|
cat << EOF >/tmp/cppcheck.sh
|
|||
|
#!/bin/bash
|
|||
|
|
|||
|
echo "Running check.sh"
|
|||
|
|
|||
|
default_ignore=(
|
|||
|
"build/"
|
|||
|
".*_test.cc"
|
|||
|
\${CPPCHECK_IGNORE[@]}
|
|||
|
)
|
|||
|
echo "default_ignore is : \${default_ignore[@]}"
|
|||
|
# 构造忽略参数
|
|||
|
ignore_args=""
|
|||
|
for ignore in \${default_ignore[@]}; do
|
|||
|
# 判断是否为目录
|
|||
|
if [ -d "\$ignore" ]; then
|
|||
|
ignore_args="-i\$ignore \$ignore_args"
|
|||
|
else
|
|||
|
files=\$(find . ! -path '*/build/*' -regex "\$ignore" -type f)
|
|||
|
for file in \$files; do
|
|||
|
ignore_args="-i\$file \$ignore_args"
|
|||
|
done
|
|||
|
fi
|
|||
|
done
|
|||
|
|
|||
|
# 如果当前目录下没有cc或者cpp或者cxx或者c文件,则直接退出,不需要进行cppcheck检查
|
|||
|
if [ -z "\$(find . -name "*.cc" -o -name "*.cpp" -o -name "*.cxx" -o -name "*.c")" ]; then
|
|||
|
echo "no cc or cpp or cxx files, not need to cppcheck"
|
|||
|
exit 0
|
|||
|
fi
|
|||
|
echo "check cmd is :"
|
|||
|
echo "cppcheck . --enable=warning,style,performance,portability,missingInclude --xml \$ignore_args"
|
|||
|
cppcheck . --enable=warning,style,performance,portability,missingInclude --xml \$ignore_args 2>/tmp/cppcheck.xml
|
|||
|
|
|||
|
|
|||
|
# 如果cppcheck检查出错,直接退出
|
|||
|
if [ \$? -ne 0 ]; then
|
|||
|
echo "cppcheck failed"
|
|||
|
exit -1
|
|||
|
fi
|
|||
|
echo "github.sha is : ${{ github.sha }}"
|
|||
|
echo "short_sha is : ${{ steps.slug.outputs.sha8 }}"
|
|||
|
|
|||
|
# 生成报告并提交到指定http文件服务器上
|
|||
|
if [ -n "${{secrets.CPPCHECK_REPORT_POST_URL}}" ]; then
|
|||
|
check_report_dir=${{ github.repository }}/${{ github.ref_name }}/${{ steps.slug.outputs.sha8 }}
|
|||
|
mkdir -p \$check_report_dir
|
|||
|
echo "github.repository_owner is : ${{ github.repository_owner }}"
|
|||
|
echo "github.repository.name is : ${{ github.repository }}"
|
|||
|
echo "github.ref_name is : ${{ github.ref_name }}"
|
|||
|
echo "steps.slug.outputs.sha8 is : ${{ steps.slug.outputs.sha8 }}"
|
|||
|
echo "check_report_dir is : \$check_report_dir"
|
|||
|
|
|||
|
cppcheck-htmlreport --file=/tmp/cppcheck.xml --title=CSA --report-dir=\$check_report_dir --source-dir=./
|
|||
|
echo "check_report_dir is : \$check_report_dir"
|
|||
|
|
|||
|
|
|||
|
# zip 压缩 \$check_report_dir
|
|||
|
zip -r \${{ steps.slug.outputs.sha8 }}.zip \$check_report_dir
|
|||
|
curl -F file=@${{ steps.slug.outputs.sha8 }}.zip -F unzip=true \${{secrets.CPPCHECK_REPORT_POST_URL}}
|
|||
|
|
|||
|
# 判断推送是否成功
|
|||
|
if [ \$? -ne 0 ]; then
|
|||
|
echo "cppcheck report push failed"
|
|||
|
exit -1
|
|||
|
fi
|
|||
|
|
|||
|
# 删除临时文件
|
|||
|
rm -rf \$check_report_dir
|
|||
|
rm -rf \${{ steps.slug.outputs.sha8 }}.zip
|
|||
|
|
|||
|
# 打印报告地址
|
|||
|
# echo "cppcheck report url: ${{secrets.CPPCHECK_REPORT_POST_URL}}/\$check_report_dir/index.html"
|
|||
|
echo -e "\\033[1;35m cppcheck report url: ${{secrets.CPPCHECK_REPORT_URL}}/\$check_report_dir/index.html \\033[0m"
|
|||
|
fi
|
|||
|
|
|||
|
EOF
|
|||
|
- name: generate cppcheck_analyze.py
|
|||
|
run: |
|
|||
|
echo "generate /tmp/cppcheck_analyze.py ..."
|
|||
|
|
|||
|
cat << EOF >/tmp/cppcheck_analyze.py
|
|||
|
#!/usr/bin/env python3
|
|||
|
|
|||
|
import os
|
|||
|
import sys
|
|||
|
import xml.dom.minidom as minidom
|
|||
|
|
|||
|
#cppcheck 所有的错误类型的严重性
|
|||
|
severityList=['information', 'performance', 'style', 'portability', 'warning', 'error']
|
|||
|
|
|||
|
informationSeverityCount = 0
|
|||
|
performanceSeverityCount = 0
|
|||
|
styleSeverityCount = 0
|
|||
|
portabilitySeverityCount = 0
|
|||
|
warningSeverityCount = 0
|
|||
|
errorSeverityCount = 0
|
|||
|
|
|||
|
# 如果 /tmp/cppcheck.xml 文件不存在,则直接退出
|
|||
|
if not os.path.exists('/tmp/cppcheck.xml'):
|
|||
|
print("/tmp/cppcheck.xml not exists")
|
|||
|
sys.exit(0)
|
|||
|
|
|||
|
# 打开cppcheck输出文件
|
|||
|
with open('/tmp/cppcheck.xml', 'r') as file:
|
|||
|
# 解析XML文件
|
|||
|
dom = minidom.parse(file)
|
|||
|
|
|||
|
# 获取所有的error元素
|
|||
|
errors = dom.getElementsByTagName('error')
|
|||
|
|
|||
|
for error in errors:
|
|||
|
# 分别统计每种严重性的错误数
|
|||
|
for i in range(len(severityList)):
|
|||
|
if error.getAttribute('severity') == severityList[i]:
|
|||
|
if i == 0:
|
|||
|
informationSeverityCount += 1
|
|||
|
elif i == 1:
|
|||
|
performanceSeverityCount += 1
|
|||
|
elif i == 2:
|
|||
|
styleSeverityCount += 1
|
|||
|
elif i == 3:
|
|||
|
portabilitySeverityCount += 1
|
|||
|
elif i == 4:
|
|||
|
warningSeverityCount += 1
|
|||
|
elif i == 5:
|
|||
|
# 如果是syntaxError则不计入errorSeverityCount
|
|||
|
if error.getAttribute('id') == 'syntaxError':
|
|||
|
continue
|
|||
|
# 如果是internalAstError则不计入errorSeverityCount
|
|||
|
if error.getAttribute('id') == 'internalAstError':
|
|||
|
continue
|
|||
|
# 如果是internalAstError则不计入errorSeverityCount
|
|||
|
if error.getAttribute('id') == 'unknownMacro':
|
|||
|
continue
|
|||
|
# 如 果msg中包含"Syntax"则不计入errorSeverityCount
|
|||
|
if error.getAttribute('msg').find("Syntax") != -1:
|
|||
|
continue
|
|||
|
errorSeverityCount += 1
|
|||
|
print(error.getAttribute('msg'))
|
|||
|
|
|||
|
# 打印结果
|
|||
|
# print(severityList)
|
|||
|
print("informationSeverityCount: ", informationSeverityCount)
|
|||
|
print("performanceSeverityCount: ", performanceSeverityCount)
|
|||
|
print("styleSeverityCount: ", styleSeverityCount)
|
|||
|
print("portabilitySeverityCount: ", portabilitySeverityCount)
|
|||
|
print("warningSeverityCount: ", warningSeverityCount)
|
|||
|
print("errorSeverityCount: ", errorSeverityCount)
|
|||
|
|
|||
|
# 获取环境变量,如果超过阈值则返回-1,否则返回0
|
|||
|
|
|||
|
|
|||
|
# 获取环境变量
|
|||
|
informationSeverityMax = os.environ.get('INFORMATION_SEVERITY_MAX')
|
|||
|
performanceSeverityMax = os.environ.get('PERFORMANCE_SEVERITY_MAX')
|
|||
|
styleSeverityMax = os.environ.get('STYLE_SEVERITY_MAX')
|
|||
|
portabilitySeverityMax = os.environ.get('PORTABILITY_SEVERITY_MAX')
|
|||
|
warningSeverityMax = os.environ.get('WARNING_SEVERITY_MAX')
|
|||
|
errorSeverityMax = os.environ.get('ERROR_SEVERITY_MAX')
|
|||
|
|
|||
|
# 如果环境变量不存在则不做处理
|
|||
|
if informationSeverityMax != None:
|
|||
|
if informationSeverityCount >= int(informationSeverityMax):
|
|||
|
print("informationSeverityCount[{}] >= informationSeverityMax[{}]".format(informationSeverityCount, informationSeverityMax))
|
|||
|
sys.exit(-1)
|
|||
|
|
|||
|
if performanceSeverityMax != None:
|
|||
|
if performanceSeverityCount >= int(performanceSeverityMax):
|
|||
|
print("performanceSeverityCount[{}] >= performanceSeverityMax[{}]".format(performanceSeverityCount, performanceSeverityMax))
|
|||
|
sys.exit(-1)
|
|||
|
|
|||
|
if styleSeverityMax != None:
|
|||
|
if styleSeverityCount >= int(styleSeverityMax):
|
|||
|
print("styleSeverityCount[{}] >= styleSeverityMax[{}]".format(styleSeverityCount, styleSeverityMax))
|
|||
|
sys.exit(-1)
|
|||
|
|
|||
|
if portabilitySeverityMax != None:
|
|||
|
if portabilitySeverityCount >= int(portabilitySeverityMax):
|
|||
|
print("portabilitySeverityCount[{}] >= portabilitySeverityMax[{}]".format(portabilitySeverityCount, portabilitySeverityMax))
|
|||
|
sys.exit(-1)
|
|||
|
|
|||
|
if warningSeverityMax != None:
|
|||
|
if warningSeverityCount >= int(warningSeverityMax):
|
|||
|
print("warningSeverityCount[{}] >= warningSeverityMax[{}]".format(warningSeverityCount, warningSeverityMax))
|
|||
|
sys.exit(-1)
|
|||
|
|
|||
|
if errorSeverityMax != None:
|
|||
|
if errorSeverityCount >= int(errorSeverityMax):
|
|||
|
print("errorSeverityCount[{}] >= errorSeverityMax[{}]".format(errorSeverityCount, errorSeverityMax))
|
|||
|
sys.exit(-1)
|
|||
|
|
|||
|
EOF
|
|||
|
- name: run cppcheck
|
|||
|
run: |
|
|||
|
chmod +x /tmp/cppcheck.sh
|
|||
|
chmod +x /tmp/cppcheck_analyze.py
|
|||
|
/tmp/cppcheck.sh
|
|||
|
/tmp/cppcheck_analyze.py
|
|||
|
|
|||
|
- name: run format
|
|||
|
run: |
|
|||
|
./format.sh
|
|||
|
git config --global --add safe.directory '*'
|
|||
|
git status
|
|||
|
if [ -n "$(git status --porcelain)" ]; then
|
|||
|
echo "check ${{ github.ref_name }} failed"
|
|||
|
exit 1
|
|||
|
fi
|
|||
|
|