Skip to content

Commit

Permalink
actions: add sloccount, prohibited-words, signed-off-by, ...
Browse files Browse the repository at this point in the history
The following TAOS-CI pr-prebuild checks are imported
- sloccount
- prohibited words
- signed off by
- shellcheck
- flawfinder
- coverity

Signed-off-by: MyungJoo Ham <[email protected]>
  • Loading branch information
myungjoo committed Feb 5, 2024
1 parent 2181080 commit 2a628fd
Show file tree
Hide file tree
Showing 7 changed files with 494 additions and 1 deletion.
122 changes: 122 additions & 0 deletions .github/workflows/static.check.scripts/flawfinder.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,122 @@
#!/usr/bin/env bash

##
# Imported from TAOS-CI
# Copyright (c) 2018 Samsung Electronics Co., Ltd. All Rights Reserved.
# Modified for Github-Action in 2024.
#
# Argument 1 ($1): the file containing the list of files to be checked
# Argument 2 ($2): the flawfinder check level. (1 by default)
#

##
# @file flawfinder.sh
# @brief This module examines C/C++ source code to find a possible security weaknesses.
# Originally, pr-prebuild-flawfinder.sh
#
# Flawfinder searches through C/C++ source code looking for potential security flaws. It examines
# all of the project's C/C++ source code. It is very useful for quickly finding and removing some
# security problems before a program is widely released.
#
# Flawfinder produces a list of `hits` (potential security flaws), sorted by risk; the riskiest
# hits are shown first. The risk level is shown inside square brackets and varies from 0 (very
# little risk) to 5 (great risk). This risk level depends not only on the function,
# but on the values of the parameters of the function. For example, constant strings are often less risky
# than fully variable strings in many contexts, and in those contexts the hit will have a lower risk level.
# Hit descriptions also note the relevant Common Weakness Enumeration (CWE) identifier(s) in parentheses.
#
# @see https://dwheeler.com/flawfinder/
# @see https://sourceforge.net/projects/flawfinder/
# @see https://github.com/nnstreamer/TAOS-CI
# @see https://github.com/nnstreamer/nnstreamer
# @author Geunsik Lim <[email protected]>
# @author MyungJoo Ham <[email protected]>

if [ -z $1 ]; then
echo "::error The argument (file path) is not given."
exit 1
fi

pr_flawfinder_check_level=1
if [ -z $2 ]; then
echo "Flawfinder check level is not given. The default value 1 is applied"
else
if [ -n "$2" ] && [ "$2" -eq "$2" ] 2>/dev/null; then
echo ""
else
echo ":error The second argument '$2' should be a number."
exit 1
fi
pr_flawfinder_check_level=$2
fi

files=$1
failed=0

if [ ! -f $files ]; then
echo "::error The file $files does not exists."
exit 1
fi

function check(){
which $1
if [[ $? -ne 0 ]]; then
echo "::error The command $1 is required, but not found."
exit 1
fi
}
# Check if server administrator install required commands
check flawfinder
check file
check grep
check cat
check wc
check git
check awk

static_analysis_sw="flawfinder"
static_analysis_rules="--html --context --minlevel=$pr_flawfinder_check_level"
flawfinder_result=$(mktemp)

# Display the flawfinder version that is installed in the CI server.
# Note that the out-of-date version can generate an incorrect result.
flawfinder --version

# Read file names that a contributor modified (e.g., added, moved, deleted, and updated) from a last commit.
# Then, inspect C/C++ source code files from *.patch files of the last commit.
for file in `cat $file`; do
# Skip the obsolete folder
if [[ $file =~ ^obsolete/.* ]]; then
continue
fi
# Skip the external folder
if [[ $file =~ ^external/.* ]]; then
continue
fi
# Handle only text files in case that there are lots of files in one commit.
if [[ `file $file | grep "ASCII text" | wc -l` -gt 0 ]]; then
# in case of C/C++ source code
case $file in
# in case of C/C++ code
*.c|*.cc|*.cpp|*.c++)
$static_analysis_sw $static_analysis_rules $file > ${flawfinder_result}
bug_nums=`cat ${flawfinder_result} | grep "Hits = " | awk '{print $3}'`
# Report the execution result.
if [[ $bug_nums -gt 0 ]]; then
echo "[ERROR] $static_analysis_sw: failed. file name: $file, There are $bug_nums bug(s)."
echo "::group::The flawfinder result of $file:"
cat ${flawfinder_result}
echo "::endgroup::"
failed=1
else
echo "[DEBUG] $static_analysis_sw: passed. file name: $file, There are $bug_nums bug(s)."
fi
;;
esac
fi
done

if [[ "$failed" == "1" ]]; then
echo "::error There is an error from flawfinder. Please review the detailed results above."
exit 1
fi
100 changes: 100 additions & 0 deletions .github/workflows/static.check.scripts/prohibited-words.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
#!/usr/bin/env bash

##
# Imported from TAOS-CI
# Copyright (c) 2018 Samsung Electronics Co., Ltd. All Rights Reserved.
# Modified for Github-Action in 2024.
#
# Argument 1 ($1): the file containing the list of files to be checked
#

##
# @file prohibited-words.sh
# @brief Check if there are prohibited words in the text files.
# Originally, pr-prebuild-prohibited-words.sh
#
# It to check a prohibited word if there are unnecessary words in the source codes.
#
# @see https://github.com/nnstreamer/TAOS-CI
# @see https://github.com/nnstreamer/nnstreamer
# @author Geunsik Lim <[email protected]>
# @author MyungJoo Ham <[email protected]>
#

if [ -z $1 ]; then
echo "::error The argument (file path) is not given."
exit 1
fi

files=$1
failed=0

if [ ! -f $files ]; then
echo "::error The file $files does not exists."
exit 1
fi

function check(){
which $1
if [[ $? -ne 0 ]]; then
echo "::error The command $1 is required, but not found."
exit 1
fi
}

check git
check grep
check wc

# Inspect all files that contributor modifed.
target_files=""
for file in `cat $files`; do
# Skip obsolete folder
if [[ $file =~ ^obsolete/.* ]]; then
continue
fi
# Skip external folder
if [[ $file =~ ^external/.* ]]; then
continue
fi
# Handle only text files among files in one commit.
if [[ `file $file | grep "ASCII text" | wc -l` -gt 0 ]]; then
case $file in
# Declare source code files to inspect a prohibited word
*.c | *.h | *.cpp | *.hpp| *.py | *.sh | *.php | *.md )
target_files="$target_files $file"
;;
esac
fi
done

bad_words_sw="grep"
bad_words_list=".github/workflows/static.check.scripts/prohibited-words.txt"
bad_words_rules="--color -n -r -H -f $bad_words_list"
bad_words_log_file=$(mktemp)

# Run a prohibited-words module in case that a PR includes text files.
if [[ -n "${target_files/[ ]*\n/}" ]]; then
if [[ ! -f $bad_words_list ]]; then
echo "::error A prohibited word list file, $bad_words_list, doesn't exist."
exit 1
fi

# Step 1: Run this module to filter prohibited words from a text file.
# (e.g., grep --color -f "$PROHIBITED_WORDS" $filename)
$bad_words_sw $bad_words_rules $target_files > ${bad_words_log_file}

# Step 2: Display the execution result for debugging in case of a failure
cat ${bad_words_log_file}

# Step 3: Count prohibited words from variable result_content
result_count=$(cat ${bad_word_log_file} | grep -c '^' )

# Step 4: change a value of the check result
if [[ $result_count -gt 0 ]]; then
echo "::error There are prohibited words in this PR (counted $result_count)."
exit 1
else
echo "There is no prohibited word found in this PR."
fi
fi
3 changes: 3 additions & 0 deletions .github/workflows/static.check.scripts/prohibited-words.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
samsung.net
FUCK
file
99 changes: 99 additions & 0 deletions .github/workflows/static.check.scripts/shellcheck.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
#!/usr/bin/env bash

##
# Imported from TAOS-CI
# Copyright (c) 2018 Samsung Electronics Co., Ltd. All Rights Reserved.
# Modified for Github-Action in 2024.
#
# Argument 1 ($1): the file containing the list of files to be checked
#

##
# @file shellcheck.sh
# @brief This module is a static analysis tool for shell scripts such as sh, bash.
# Originally, pr-prebuild-shellcheck.sh
#
# It is mainly focused on handling typical beginner and intermediate level syntax errors
# and pitfalls where the shell just gives a cryptic error message or strange behavior,
# but it also reports on a few more advanced issues where corner cases can cause delayed
# failures.
#
# @see https://www.shellcheck.net/
# @see https://github.com/nnstreamer/TAOS-CI
# @see https://github.com/nnstreamer/nnstreamer
# @author Geunsik Lim <[email protected]>
# @author MyungJoo Ham <[email protected]>
#

if [ -z $1 ]; then
echo "::error The argument (file path) is not given."
exit 1
fi

files=$1
failed=0

if [ ! -f $files ]; then
echo "::error The file $files does not exists."
exit 1
fi

function check(){
which $1
if [[ $? -ne 0 ]]; then
echo "::error The command $1 is required, but not found."
exit 1
fi
}
# Check if required commands are installed by server administrator
check cat
check shellcheck
check file
check grep
check wc

shell_syntax_analysis_sw="shellcheck"
shell_syntax_analysis_rules="-s bash"
shell_syntax_check_result=$(mktemp)

# Inspect all files that contributor modifed.
for file in `cat $files`; do
# Skip obsolete folder
if [[ $file =~ ^obsolete/.* ]]; then
continue
fi
# Skip external folder
if [[ $file =~ ^external/.* ]]; then
continue
fi
# Handle only text files in case that there are lots of files in one commit.
echo "[DEBUG] file name is ($file)."
if [[ `file $file | grep "shell script" | wc -l` -gt 0 ]]; then
case $file in
# In case of .sh or .bash file
*.sh | *.bash)
echo "($file) file is a shell script file with the 'shell script' text format."

cat $file | $shell_syntax_analysis_sw $shell_syntax_analysis_rules > ${shell_syntax_check_result}
line_count=`cat ${shell_syntax_check_result} | wc -l`

echo "::group::shellcheck result of $file"
cat ${shell_syntax_check_result}
echo "::endgroup::"

# TODO: 9,000 is declared by heuristic method from our experiment.
if [[ $line_count -gt 9000 ]]; then
echo "$shell_syntax_analysis_sw: failed. file name: $file There are $line_count lines."
failed=1
else
echo "$shell_syntax_analysis_sw: passed. file name: $file There are $line_count lines."
fi
;;
esac
fi
done

if [[ "$failed" == "1" ]]; then
echo "::error These is a enough number of errors in a shell file with shellcheck. Please refer to the log above".
exit 1
fi
55 changes: 55 additions & 0 deletions .github/workflows/static.check.scripts/signed-off-by.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
#!/usr/bin/env bash

##
# Imported from TAOS-CI
# Copyright (c) 2018 Samsung Electronics Co., Ltd. All Rights Reserved.
# Modified for Github-Action in 2024.
#
# Argument 1 ($1): the number of commits in this PR
#

##
# @file signed-off-by.sh
# @brief Check if contributor write Sigend-off-by message. Originally, pr-prebuild-signed-off-by.sh
# @see https://github.com/nnstreamer/TAOS-CI
# @see https://github.com/nnstreamer/nnstreamer
# @author Sewon oh <[email protected]>
# @author MyungJoo Ham <[email protected]>
#

if [ -z $1 ]; then
echo "::error The argument (the number of commits in this PR) is not given."
exit 1
fi

if [ -n "$1" ] && [ "$1" -eq "$1" ] 2>/dev/null; then
echo ""
else
echo ":error The first argument '$1' should be a number."
exit 1
fi

function check(){
which $1
if [[ $? -ne 0 ]]; then
echo "::error The command $1 is required, but not found."
exit 1
fi
}

# Check if server administrator install required commands
check git

for i in $(seq 0 $[$1 - 1]); do
count=`git show --no-notes -s HEAD~$i | grep "Signed-off-by: [^ ].*[^ ].*<[^ ].*@[^ ].*>" | wc -l`
if [[ $count -lt 1 ]]; then
git show --stat HEAD~$i
echo "============================================"
echo ""
echo "::error This commit does not have a proper Signed-off-by. Refer to https://ltsi.linuxfoundation.org/software/signed-off-process/ for some information about Signed-off-by. We require Signed-off-by: NAME <EMAIL> signed by indivisual contributors."
exit 1
else
id=`git show --pretty="format:%h" --no-notes -s HEAD~$i`
echo "Commit $id has proper a signed-off-by string."
fi
done
Loading

0 comments on commit 2a628fd

Please sign in to comment.