2 # Desc: Runs gpg --verify on all .asc, .gpg, and .sig files in specified directory.
4 # Depends: GNU parallel 20210822
5 # Assumes: File names do not contain newlines.
7 declare -Ag appRollCall
# Associative array for storing app status
8 declare -Ag fileRollCall
# Associative array for storing file status
9 declare -Ag dirRollCall
# Associative array for storing dir status
10 find_pat_regex
=".+\(sig\|asc\|gpg\)$";
13 yell
() { echo "$0: $*" >&2; } # print script path and all args to stderr
14 die
() { yell
"$*"; exit 111; } # same as yell() but non-zero exit status
15 must
() { "$@" || die
"cannot $*"; } # runs args as command, reports args if command fails
17 # Desc: If arg is a command, save result in assoc array 'appRollCall'
18 # Usage: checkapp arg1 arg2 arg3 ...
20 # Input: global assoc. array 'appRollCall'
21 # Output: adds/updates key(value) to global assoc array 'appRollCall'
27 if command -v "$arg" 1>/dev
/null
2>&1; then # Check if arg is a valid command
28 appRollCall
[$arg]="true";
29 if ! [ "$returnState" = "false" ]; then returnState
="true"; fi;
31 appRollCall
[$arg]="false"; returnState
="false";
35 #===Determine function return code===
36 if [ "$returnState" = "true" ]; then
41 } # Check that app exists
43 # Desc: If arg is a file path, save result in assoc array 'fileRollCall'
44 # Usage: checkfile arg1 arg2 arg3 ...
46 # Input: global assoc. array 'fileRollCall'
47 # Output: adds/updates key(value) to global assoc array 'fileRollCall';
48 # Output: returns 0 if app found, 1 otherwise
54 if [ -f "$arg" ]; then
55 fileRollCall
["$arg"]="true";
56 if ! [ "$returnState" = "false" ]; then returnState
="true"; fi;
57 elif [ -z "$arg" ]; then
58 fileRollCall
["(no name)"]="false"; returnState
="false";
60 fileRollCall
["$arg"]="false"; returnState
="false";
64 #===Determine function return code===
65 if [ "$returnState" = "true" ]; then
70 } # Check that file exists
72 # Desc: If arg is a dir path, save result in assoc array 'dirRollCall'
73 # Usage: checkdir arg1 arg2 arg3 ...
75 # Input: global assoc. array 'dirRollCall'
76 # Output: adds/updates key(value) to global assoc array 'dirRollCall';
77 # Output: returns 0 if all args are dirs; 1 otherwise
83 if [ -z "$arg" ]; then
84 dirRollCall
["(Unspecified Dirname(s))"]="false"; returnState
="false";
85 elif [ -d "$arg" ]; then
86 dirRollCall
["$arg"]="true";
87 if ! [ "$returnState" = "false" ]; then returnState
="true"; fi
89 dirRollCall
["$arg"]="false"; returnState
="false";
93 #===Determine function return code===
94 if [ "$returnState" = "true" ]; then
99 } # Check that dir exists
101 # Desc: Displays missing apps, files, and dirs
102 # Usage: displayMissing
104 # Input: associative arrays: appRollCall, fileRollCall, dirRollCall
105 # Output: stderr: messages indicating missing apps, file, or dirs
106 # Output: returns exit code 0 if nothing missing; 1 otherwise
107 # Depends: bash 5, checkAppFileDir()
108 local missingApps value appMissing missingFiles fileMissing
109 local missingDirs dirMissing
111 #==BEGIN Display errors==
112 #===BEGIN Display Missing Apps===
113 missingApps
="Missing apps :";
114 #for key in "${!appRollCall[@]}"; do echo "DEBUG:$key => ${appRollCall[$key]}"; done
115 for key
in "${!appRollCall[@]}"; do
116 value
="${appRollCall[$key]}";
117 if [ "$value" = "false" ]; then
118 #echo "DEBUG:Missing apps: $key => $value";
119 missingApps
="$missingApps""$key ";
123 if [ "$appMissing" = "true" ]; then # Only indicate if an app is missing.
124 echo "$missingApps" 1>&2;
127 #===END Display Missing Apps===
129 #===BEGIN Display Missing Files===
130 missingFiles
="Missing files:";
131 #for key in "${!fileRollCall[@]}"; do echo "DEBUG:$key => ${fileRollCall[$key]}"; done
132 for key
in "${!fileRollCall[@]}"; do
133 value
="${fileRollCall[$key]}";
134 if [ "$value" = "false" ]; then
135 #echo "DEBUG:Missing files: $key => $value";
136 missingFiles
="$missingFiles""$key ";
140 if [ "$fileMissing" = "true" ]; then # Only indicate if an app is missing.
141 echo "$missingFiles" 1>&2;
144 #===END Display Missing Files===
146 #===BEGIN Display Missing Directories===
147 missingDirs
="Missing dirs:";
148 #for key in "${!dirRollCall[@]}"; do echo "DEBUG:$key => ${dirRollCall[$key]}"; done
149 for key
in "${!dirRollCall[@]}"; do
150 value
="${dirRollCall[$key]}";
151 if [ "$value" = "false" ]; then
152 #echo "DEBUG:Missing dirs: $key => $value";
153 missingDirs
="$missingDirs""$key ";
157 if [ "$dirMissing" = "true" ]; then # Only indicate if an dir is missing.
158 echo "$missingDirs" 1>&2;
161 #===END Display Missing Directories===
163 #==END Display errors==
164 #==BEGIN Determine function return code===
165 if [ "$appMissing" == "true" ] ||
[ "$fileMissing" == "true" ] ||
[ "$dirMissing" == "true" ]; then
170 #==END Determine function return code===
171 } # Display missing apps, files, dirs
173 # input: arg1: file path
177 if gpg
--verify "$path_in" 1>&2 2>/dev
/random
; then
178 printf "STATUS:Good sig for:%s\n" "$path_in";
180 printf "STATUS:Bad sig for :%s\n" "$path_in";
182 }; # verfiies one gpg file
185 ## Note: Assume a single arg that is a dir
186 if [[ ! $# -eq 1 ]]; then die
"FATAL:Incorrect number of args (must be 1):$#"; fi;
187 if [[ ! -d "$1" ]]; then die
"FATAL:Not a dir:$1"; fi;
190 if ! checkapp
find gpg parallel
; then displayMissing
; printf "FATAL:Missing apps."; exit 1; fi;
192 # Export bash functions (for GNU parallel)
193 export -f yell die must verify_file
;
196 list_paths
="$( find "$1" -maxdepth "$find_depth" -type f -iregex "$find_pat_regex" )";
199 echo "$list_paths" | parallel
--group verify_file
'{}';
206 # find "$1" -maxdepth "$find_depth" -type f -iregex "find_pat_regex" | parallel if gpg --verify '{}' 2>/dev/random \; then echo "STATUS:Good sig:" '{}' \; else echo "STATUS:Bad sig :" '{}' \; fi\;