security revision 1.27 1 1.1 cgd #!/bin/sh -
2 1.1 cgd #
3 1.27 lukem # $NetBSD: security,v 1.27 1997/08/22 09:40:17 lukem Exp $
4 1.9 cgd # from: @(#)security 8.1 (Berkeley) 6/9/93
5 1.1 cgd #
6 1.1 cgd
7 1.9 cgd PATH=/sbin:/usr/sbin:/bin:/usr/bin
8 1.1 cgd
9 1.9 cgd umask 077
10 1.1 cgd
11 1.15 mrg if [ -s /etc/security.conf ]; then
12 1.15 mrg . /etc/security.conf
13 1.15 mrg fi
14 1.15 mrg
15 1.15 mrg SECUREDIR=/tmp/_securedir.$$
16 1.15 mrg if ! mkdir $SECUREDIR; then
17 1.15 mrg echo can not create $SECUREDIR.
18 1.15 mrg exit 1
19 1.15 mrg fi
20 1.15 mrg
21 1.15 mrg if ! cd $SECUREDIR; then
22 1.15 mrg echo can not chdir to $SECUREDIR.
23 1.15 mrg exit 1
24 1.15 mrg fi
25 1.15 mrg
26 1.15 mrg ERR=secure1.$$
27 1.15 mrg TMP1=secure2.$$
28 1.15 mrg TMP2=secure3.$$
29 1.27 lukem MPUID=secure4.$$
30 1.27 lukem MPPATH=secure5.$$
31 1.27 lukem LIST=secure6.$$
32 1.27 lukem OUTPUT=secure7.$$
33 1.15 mrg
34 1.27 lukem trap '/bin/rm -rf $SECUREDIR ; exit 0' 0 2 3
35 1.15 mrg
36 1.15 mrg MP=/etc/master.passwd
37 1.9 cgd
38 1.27 lukem # these is used several times.
39 1.27 lukem awk -F: '{ print $1 " " $3 }' $MP | sort -k2n > $MPUID
40 1.27 lukem awk -F: '{ print $1 " " $9 }' $MP | sort -k2 > $MPPATH
41 1.9 cgd
42 1.9 cgd # Check the master password file syntax.
43 1.17 mycroft if [ "$check_passwd" = YES ]; then
44 1.25 lukem awk '
45 1.25 lukem BEGIN {
46 1.25 lukem while ( getline < "/etc/shells" > 0 ) {
47 1.25 lukem if ($LINE ~ /^\#/ || $LINE ~ /^$/ )
48 1.25 lukem continue;
49 1.25 lukem shells[$1]++;
50 1.25 lukem }
51 1.25 lukem FS=":";
52 1.25 lukem }
53 1.25 lukem
54 1.25 lukem {
55 1.15 mrg if ($0 ~ /^[ ]*$/) {
56 1.25 lukem printf "Line %d is a blank line.\n", NR;
57 1.15 mrg next;
58 1.15 mrg }
59 1.15 mrg if (NF != 10)
60 1.25 lukem printf "Line %d has the wrong number of fields.\n", NR;
61 1.15 mrg if ($1 !~ /^[A-Za-z0-9]*$/)
62 1.25 lukem printf "Login %s has non-alphanumeric characters.\n",
63 1.25 lukem $1;
64 1.15 mrg if (length($1) > 8)
65 1.25 lukem printf "Login %s has more than 8 characters.\n", $1;
66 1.15 mrg if ($2 == "")
67 1.25 lukem printf "Login %s has no password.\n", $1;
68 1.25 lukem if (length($2) != 13 && $2 != "") {
69 1.25 lukem if ($10 == "" || shells[$10])
70 1.27 lukem printf "Login %s is off but still has a valid shell (%s)\n",
71 1.25 lukem $1, $10;
72 1.25 lukem } else if (! shells[$10])
73 1.25 lukem printf "Login %s does not have a valid shell (%s)\n",
74 1.25 lukem $1, $10;
75 1.15 mrg if ($3 == 0 && $1 != "root" && $1 != "toor")
76 1.25 lukem printf "Login %s has a user id of 0.\n", $1;
77 1.15 mrg if ($3 < 0)
78 1.25 lukem printf "Login %s has a negative user id.\n", $1;
79 1.15 mrg if ($4 < 0)
80 1.25 lukem printf "Login %s has a negative group id.\n", $1;
81 1.15 mrg }' < $MP > $OUTPUT
82 1.15 mrg if [ -s $OUTPUT ] ; then
83 1.15 mrg printf "\nChecking the $MP file:\n"
84 1.15 mrg cat $OUTPUT
85 1.15 mrg fi
86 1.15 mrg
87 1.15 mrg awk -F: '{ print $1 }' $MP | sort | uniq -d > $OUTPUT
88 1.15 mrg if [ -s $OUTPUT ] ; then
89 1.15 mrg printf "\n$MP has duplicate user names.\n"
90 1.15 mrg column $OUTPUT
91 1.15 mrg fi
92 1.15 mrg
93 1.27 lukem < $MPUID uniq -d -f 1 | awk '{ print $2 }' > $TMP2
94 1.15 mrg if [ -s $TMP2 ] ; then
95 1.15 mrg printf "\n$MP has duplicate user id's.\n"
96 1.15 mrg while read uid; do
97 1.27 lukem grep -w $uid $MPUID
98 1.15 mrg done < $TMP2 | column
99 1.15 mrg fi
100 1.9 cgd fi
101 1.9 cgd
102 1.9 cgd # Backup the master password file; a special case, the normal backup
103 1.9 cgd # mechanisms also print out file differences and we don't want to do
104 1.9 cgd # that because this file has encrypted passwords in it.
105 1.9 cgd CUR=/var/backups/`basename $MP`.current
106 1.9 cgd BACK=/var/backups/`basename $MP`.backup
107 1.9 cgd if [ -s $CUR ] ; then
108 1.9 cgd if cmp -s $CUR $MP; then
109 1.9 cgd :
110 1.9 cgd else
111 1.9 cgd cp -p $CUR $BACK
112 1.9 cgd cp -p $MP $CUR
113 1.9 cgd chown root.wheel $CUR
114 1.9 cgd fi
115 1.9 cgd else
116 1.9 cgd cp -p $MP $CUR
117 1.9 cgd chown root.wheel $CUR
118 1.9 cgd fi
119 1.9 cgd
120 1.9 cgd # Check the group file syntax.
121 1.17 mycroft if [ "$check_group" = YES ]; then
122 1.15 mrg GRP=/etc/group
123 1.15 mrg awk -F: '{
124 1.15 mrg if ($0 ~ /^[ ]*$/) {
125 1.25 lukem printf "Line %d is a blank line.\n", NR;
126 1.15 mrg next;
127 1.15 mrg }
128 1.15 mrg if (NF != 4)
129 1.25 lukem printf "Line %d has the wrong number of fields.\n", NR;
130 1.15 mrg if ($1 !~ /^[A-za-z0-9]*$/)
131 1.25 lukem printf "Group %s has non-alphanumeric characters.\n",
132 1.25 lukem $1;
133 1.15 mrg if (length($1) > 8)
134 1.25 lukem printf "Group %s has more than 8 characters.\n", $1;
135 1.15 mrg if ($3 !~ /[0-9]*/)
136 1.25 lukem printf "Login %s has a negative group id.\n", $1;
137 1.15 mrg }' < $GRP > $OUTPUT
138 1.15 mrg if [ -s $OUTPUT ] ; then
139 1.15 mrg printf "\nChecking the $GRP file:\n"
140 1.15 mrg cat $OUTPUT
141 1.15 mrg fi
142 1.15 mrg
143 1.15 mrg awk -F: '{ print $1 }' $GRP | sort | uniq -d > $OUTPUT
144 1.15 mrg if [ -s $OUTPUT ] ; then
145 1.15 mrg printf "\n$GRP has duplicate group names.\n"
146 1.15 mrg column $OUTPUT
147 1.15 mrg fi
148 1.9 cgd fi
149 1.9 cgd
150 1.9 cgd # Check for root paths, umask values in startup files.
151 1.9 cgd # The check for the root paths is problematical -- it's likely to fail
152 1.9 cgd # in other environments. Once the shells have been modified to warn
153 1.9 cgd # of '.' in the path, the path tests should go away.
154 1.17 mycroft if [ "$check_rootdotfiles" = YES ]; then
155 1.15 mrg cp /dev/null $OUTPUT
156 1.15 mrg rhome=`csh -fc "echo ~root"`
157 1.15 mrg umaskset=no
158 1.15 mrg list="/etc/csh.cshrc /etc/csh.login ${rhome}/.cshrc ${rhome}/.login"
159 1.15 mrg for i in $list ; do
160 1.15 mrg if [ -f $i ] ; then
161 1.15 mrg if egrep umask $i > /dev/null ; then
162 1.15 mrg umaskset=yes
163 1.15 mrg fi
164 1.15 mrg egrep umask $i |
165 1.15 mrg awk '$2 % 100 < 20 \
166 1.27 lukem { print "\tRoot umask is group writeable" }
167 1.15 mrg $2 % 10 < 2 \
168 1.27 lukem { print "\tRoot umask is other writeable" }' \
169 1.27 lukem >> $OUTPUT
170 1.26 lukem SAVE_PATH=$PATH
171 1.26 lukem unset PATH
172 1.15 mrg /bin/csh -f -s << end-of-csh > /dev/null 2>&1
173 1.15 mrg source $i
174 1.15 mrg /bin/ls -ldgT \$path > $TMP1
175 1.9 cgd end-of-csh
176 1.26 lukem PATH=$SAVE_PATH
177 1.15 mrg awk '{
178 1.15 mrg if ($10 ~ /^\.$/) {
179 1.27 lukem print "\tThe root path includes .";
180 1.15 mrg next;
181 1.15 mrg }
182 1.15 mrg }
183 1.15 mrg $1 ~ /^d....w/ \
184 1.27 lukem { print "\tRoot path directory " $10 " is group writeable." } \
185 1.15 mrg $1 ~ /^d.......w/ \
186 1.27 lukem { print "\tRoot path directory " $10 " is other writeable." }' \
187 1.15 mrg < $TMP1 >> $OUTPUT
188 1.15 mrg fi
189 1.15 mrg done
190 1.15 mrg if [ $umaskset = "no" -o -s $OUTPUT ] ; then
191 1.27 lukem printf "\nChecking root csh paths, umask values:\n$list\n\n"
192 1.15 mrg if [ -s $OUTPUT ]; then
193 1.15 mrg cat $OUTPUT
194 1.15 mrg fi
195 1.15 mrg if [ $umaskset = "no" ] ; then
196 1.27 lukem printf "\tRoot csh startup files do not set the umask.\n"
197 1.15 mrg fi
198 1.9 cgd fi
199 1.9 cgd
200 1.15 mrg cp /dev/null $OUTPUT
201 1.15 mrg rhome=/root
202 1.15 mrg umaskset=no
203 1.23 lukem list="/etc/profile ${rhome}/.profile"
204 1.15 mrg for i in $list; do
205 1.15 mrg if [ -f $i ] ; then
206 1.15 mrg if egrep umask $i > /dev/null ; then
207 1.15 mrg umaskset=yes
208 1.15 mrg fi
209 1.15 mrg egrep umask $i |
210 1.15 mrg awk '$2 % 100 < 20 \
211 1.27 lukem { print "\tRoot umask is group writeable" } \
212 1.15 mrg $2 % 10 < 2 \
213 1.27 lukem { print "\tRoot umask is other writeable" }' \
214 1.27 lukem >> $OUTPUT
215 1.26 lukem SAVE_PATH=$PATH
216 1.26 lukem unset PATH
217 1.15 mrg /bin/sh << end-of-sh > /dev/null 2>&1
218 1.15 mrg . $i
219 1.26 lukem list=\`echo \$PATH | /usr/bin/sed -e \
220 1.26 lukem 's/^:/.:/;s/:$/:./;s/::/:.:/g;s/:/ /g'\`
221 1.15 mrg /bin/ls -ldgT \$list > $TMP1
222 1.9 cgd end-of-sh
223 1.26 lukem PATH=$SAVE_PATH
224 1.15 mrg awk '{
225 1.15 mrg if ($10 ~ /^\.$/) {
226 1.27 lukem print "\tThe root path includes .";
227 1.15 mrg next;
228 1.15 mrg }
229 1.15 mrg }
230 1.15 mrg $1 ~ /^d....w/ \
231 1.27 lukem { print "\tRoot path directory " $10 " is group writeable." } \
232 1.15 mrg $1 ~ /^d.......w/ \
233 1.27 lukem { print "\tRoot path directory " $10 " is other writeable." }' \
234 1.15 mrg < $TMP1 >> $OUTPUT
235 1.9 cgd
236 1.15 mrg fi
237 1.15 mrg done
238 1.15 mrg if [ $umaskset = "no" -o -s $OUTPUT ] ; then
239 1.15 mrg printf "\nChecking root sh paths, umask values:\n$list\n"
240 1.15 mrg if [ -s $OUTPUT ]; then
241 1.15 mrg cat $OUTPUT
242 1.15 mrg fi
243 1.15 mrg if [ $umaskset = "no" ] ; then
244 1.27 lukem printf "\tRoot sh startup files do not set the umask.\n"
245 1.15 mrg fi
246 1.9 cgd fi
247 1.9 cgd fi
248 1.9 cgd
249 1.9 cgd # Root and uucp should both be in /etc/ftpusers.
250 1.27 lukem # XXX This should be updated to support the new format...
251 1.17 mycroft if [ "$check_ftpusers" = YES ]; then
252 1.27 lukem list="root uucp"
253 1.27 lukem for i in $list; do
254 1.27 lukem if ! egrep "^$i$" /etc/ftpusers > /dev/null ; then
255 1.27 lukem printf "\n$i is not listed in /etc/ftpusers file.\n"
256 1.27 lukem fi
257 1.27 lukem done
258 1.9 cgd fi
259 1.9 cgd
260 1.9 cgd # Uudecode should not be in the /etc/aliases file.
261 1.17 mycroft if [ "$check_aliases" = YES ]; then
262 1.18 mikel if egrep '^[^#]*(uudecode|decode).*\|' /etc/aliases; then
263 1.18 mikel printf "\nEntry for uudecode in /etc/aliases file.\n"
264 1.15 mrg fi
265 1.9 cgd fi
266 1.9 cgd
267 1.9 cgd # Files that should not have + signs.
268 1.17 mycroft if [ "$check_rhosts" = YES ]; then
269 1.15 mrg list="/etc/hosts.equiv /etc/hosts.lpd"
270 1.15 mrg for f in $list ; do
271 1.15 mrg if [ -f $f ] && egrep '\+' $f > /dev/null ; then
272 1.15 mrg printf "\nPlus sign in $f file.\n"
273 1.15 mrg fi
274 1.15 mrg done
275 1.15 mrg
276 1.15 mrg # Check for special users with .rhosts files. Only root and toor should
277 1.16 mikel # have .rhosts files. Also, .rhosts files should not have plus signs.
278 1.15 mrg awk -F: '$1 != "root" && $1 != "toor" && \
279 1.15 mrg ($3 < 100 || $1 == "ftp" || $1 == "uucp") \
280 1.20 mycroft { print $1 " " $9 }' $MP |
281 1.19 mycroft sort -k2 |
282 1.15 mrg while read uid homedir; do
283 1.15 mrg if [ -f ${homedir}/.rhosts ] ; then
284 1.15 mrg rhost=`ls -ldgT ${homedir}/.rhosts`
285 1.15 mrg printf "$uid: $rhost\n"
286 1.15 mrg fi
287 1.15 mrg done > $OUTPUT
288 1.15 mrg if [ -s $OUTPUT ] ; then
289 1.15 mrg printf "\nChecking for special users with .rhosts files.\n"
290 1.15 mrg cat $OUTPUT
291 1.15 mrg fi
292 1.15 mrg
293 1.15 mrg while read uid homedir; do
294 1.15 mrg if [ -f ${homedir}/.rhosts ] && \
295 1.15 mrg egrep '\+' ${homedir}/.rhosts > /dev/null ; then
296 1.15 mrg printf "$uid: + in .rhosts file.\n"
297 1.15 mrg fi
298 1.27 lukem done < $MPPATH > $OUTPUT
299 1.15 mrg if [ -s $OUTPUT ] ; then
300 1.15 mrg printf "\nChecking .rhosts files syntax.\n"
301 1.15 mrg cat $OUTPUT
302 1.15 mrg fi
303 1.9 cgd fi
304 1.9 cgd
305 1.9 cgd # Check home directories. Directories should not be owned by someone else
306 1.9 cgd # or writeable.
307 1.17 mycroft if [ "$check_homes" = YES ]; then
308 1.15 mrg while read uid homedir; do
309 1.15 mrg if [ -d ${homedir}/ ] ; then
310 1.15 mrg file=`ls -ldgT ${homedir}`
311 1.15 mrg printf "$uid $file\n"
312 1.9 cgd fi
313 1.27 lukem done < $MPPATH |
314 1.15 mrg awk '$1 != $4 && $4 != "root" \
315 1.15 mrg { print "user " $1 " home directory is owned by " $4 }
316 1.15 mrg $2 ~ /^-....w/ \
317 1.15 mrg { print "user " $1 " home directory is group writeable" }
318 1.15 mrg $2 ~ /^-.......w/ \
319 1.27 lukem { print "user " $1 " home directory is other writeable" }' \
320 1.27 lukem > $OUTPUT
321 1.15 mrg if [ -s $OUTPUT ] ; then
322 1.15 mrg printf "\nChecking home directories.\n"
323 1.15 mrg cat $OUTPUT
324 1.15 mrg fi
325 1.15 mrg
326 1.15 mrg # Files that should not be owned by someone else or readable.
327 1.27 lukem list=".Xauthority .netrc"
328 1.15 mrg while read uid homedir; do
329 1.15 mrg for f in $list ; do
330 1.15 mrg file=${homedir}/${f}
331 1.15 mrg if [ -f $file ] ; then
332 1.15 mrg printf "$uid $f `ls -ldgT $file`\n"
333 1.15 mrg fi
334 1.15 mrg done
335 1.27 lukem done < $MPPATH |
336 1.15 mrg awk '$1 != $5 && $5 != "root" \
337 1.15 mrg { print "user " $1 " " $2 " file is owned by " $5 }
338 1.15 mrg $3 ~ /^-...r/ \
339 1.15 mrg { print "user " $1 " " $2 " file is group readable" }
340 1.15 mrg $3 ~ /^-......r/ \
341 1.15 mrg { print "user " $1 " " $2 " file is other readable" }
342 1.15 mrg $3 ~ /^-....w/ \
343 1.15 mrg { print "user " $1 " " $2 " file is group writeable" }
344 1.15 mrg $3 ~ /^-.......w/ \
345 1.27 lukem { print "user " $1 " " $2 " file is other writeable" }' \
346 1.27 lukem > $OUTPUT
347 1.15 mrg
348 1.15 mrg # Files that should not be owned by someone else or writeable.
349 1.19 mycroft list=".bash_history .bash_login .bash_logout .bash_profile .bashrc \
350 1.19 mycroft .cshrc .emacs .exrc .forward .history .klogin .login .logout \
351 1.27 lukem .profile .qmail .rc_history .rhosts .tcshrc .twmrc .xinitrc \
352 1.27 lukem .xsession"
353 1.15 mrg while read uid homedir; do
354 1.15 mrg for f in $list ; do
355 1.15 mrg file=${homedir}/${f}
356 1.15 mrg if [ -f $file ] ; then
357 1.15 mrg printf "$uid $f `ls -ldgT $file`\n"
358 1.15 mrg fi
359 1.15 mrg done
360 1.27 lukem done < $MPPATH |
361 1.15 mrg awk '$1 != $5 && $5 != "root" \
362 1.15 mrg { print "user " $1 " " $2 " file is owned by " $5 }
363 1.15 mrg $3 ~ /^-....w/ \
364 1.15 mrg { print "user " $1 " " $2 " file is group writeable" }
365 1.15 mrg $3 ~ /^-.......w/ \
366 1.27 lukem { print "user " $1 " " $2 " file is other writeable" }' \
367 1.27 lukem >> $OUTPUT
368 1.15 mrg if [ -s $OUTPUT ] ; then
369 1.15 mrg printf "\nChecking dot files.\n"
370 1.15 mrg cat $OUTPUT
371 1.15 mrg fi
372 1.9 cgd fi
373 1.9 cgd
374 1.9 cgd # Mailboxes should be owned by user and unreadable.
375 1.17 mycroft if [ "$check_varmail" = YES ]; then
376 1.15 mrg ls -l /var/mail | sed 1d | \
377 1.15 mrg awk '$3 != $9 \
378 1.15 mrg { print "user " $9 " mailbox is owned by " $3 }
379 1.15 mrg $1 != "-rw-------" \
380 1.15 mrg { print "user " $9 " mailbox is " $1 ", group " $4 }' > $OUTPUT
381 1.15 mrg if [ -s $OUTPUT ] ; then
382 1.15 mrg printf "\nChecking mailbox ownership.\n"
383 1.15 mrg cat $OUTPUT
384 1.15 mrg fi
385 1.15 mrg fi
386 1.15 mrg
387 1.17 mycroft if [ "$check_nfs" = YES ]; then
388 1.15 mrg if [ -f /etc/exports ]; then
389 1.15 mrg # File systems should not be globally exported.
390 1.15 mrg awk '{
391 1.22 lukem # ignore comments and blank lines
392 1.22 lukem if ($LINE ~ /^\#/ || $LINE ~ /^$/ )
393 1.22 lukem next;
394 1.22 lukem
395 1.15 mrg readonly = 0;
396 1.15 mrg for (i = 2; i <= NF; ++i) {
397 1.15 mrg if ($i ~ /-ro/)
398 1.15 mrg readonly = 1;
399 1.15 mrg else if ($i !~ /^-/)
400 1.15 mrg next;
401 1.15 mrg }
402 1.15 mrg if (readonly)
403 1.15 mrg print "File system " $1 " globally exported, read-only."
404 1.15 mrg else
405 1.15 mrg print "File system " $1 " globally exported, read-write."
406 1.15 mrg }' < /etc/exports > $OUTPUT
407 1.15 mrg if [ -s $OUTPUT ] ; then
408 1.15 mrg printf "\nChecking for globally exported file systems.\n"
409 1.15 mrg cat $OUTPUT
410 1.15 mrg fi
411 1.15 mrg fi
412 1.9 cgd fi
413 1.9 cgd
414 1.9 cgd # Display any changes in setuid files and devices.
415 1.17 mycroft if [ "$check_devices" = YES ]; then
416 1.15 mrg printf "\nChecking setuid files and devices:\n"
417 1.15 mrg (find / \( ! -fstype local -o -fstype fdesc -o -fstype kernfs \
418 1.15 mrg -o -fstype procfs \) -a -prune -o \
419 1.21 mycroft \( \( -perm -u+s -a ! -type d \) -o \
420 1.21 mycroft \( -perm -g+s -a ! -type d \) -o \
421 1.24 lukem -type b -o -type c \) -print0 | \
422 1.24 lukem xargs -0 ls -ldgTq | sort +9 > $LIST) 2> $OUTPUT
423 1.15 mrg
424 1.15 mrg # Display any errors that occurred during system file walk.
425 1.15 mrg if [ -s $OUTPUT ] ; then
426 1.15 mrg printf "Setuid/device find errors:\n"
427 1.15 mrg cat $OUTPUT
428 1.15 mrg printf "\n"
429 1.15 mrg fi
430 1.15 mrg
431 1.15 mrg # Display any changes in the setuid file list.
432 1.15 mrg egrep -v '^[bc]' $LIST > $TMP1
433 1.15 mrg if [ -s $TMP1 ] ; then
434 1.15 mrg # Check to make sure uudecode isn't setuid.
435 1.15 mrg if grep -w uudecode $TMP1 > /dev/null ; then
436 1.15 mrg printf "\nUudecode is setuid.\n"
437 1.15 mrg fi
438 1.15 mrg
439 1.15 mrg CUR=/var/backups/setuid.current
440 1.15 mrg BACK=/var/backups/setuid.backup
441 1.9 cgd
442 1.15 mrg if [ -s $CUR ] ; then
443 1.15 mrg if cmp -s $CUR $TMP1 ; then
444 1.15 mrg :
445 1.15 mrg else
446 1.15 mrg > $TMP2
447 1.15 mrg join -110 -210 -v2 $CUR $TMP1 > $OUTPUT
448 1.15 mrg if [ -s $OUTPUT ] ; then
449 1.15 mrg printf "Setuid additions:\n"
450 1.15 mrg tee -a $TMP2 < $OUTPUT
451 1.15 mrg printf "\n"
452 1.15 mrg fi
453 1.15 mrg
454 1.15 mrg join -110 -210 -v1 $CUR $TMP1 > $OUTPUT
455 1.15 mrg if [ -s $OUTPUT ] ; then
456 1.15 mrg printf "Setuid deletions:\n"
457 1.15 mrg tee -a $TMP2 < $OUTPUT
458 1.15 mrg printf "\n"
459 1.15 mrg fi
460 1.15 mrg
461 1.20 mycroft sort -k10 $TMP2 $CUR $TMP1 | \
462 1.27 lukem sed -e 's/[ ][ ]*/ /g' | \
463 1.27 lukem uniq -u > $OUTPUT
464 1.15 mrg if [ -s $OUTPUT ] ; then
465 1.15 mrg printf "Setuid changes:\n"
466 1.15 mrg column -t $OUTPUT
467 1.15 mrg printf "\n"
468 1.15 mrg fi
469 1.9 cgd
470 1.15 mrg cp $CUR $BACK
471 1.15 mrg cp $TMP1 $CUR
472 1.9 cgd fi
473 1.15 mrg else
474 1.15 mrg printf "Setuid additions:\n"
475 1.15 mrg column -t $TMP1
476 1.15 mrg printf "\n"
477 1.9 cgd cp $TMP1 $CUR
478 1.9 cgd fi
479 1.15 mrg fi
480 1.15 mrg
481 1.27 lukem # Check for block and character disk devices that are readable or
482 1.27 lukem # writeable or not owned by root.operator.
483 1.15 mrg >$TMP1
484 1.27 lukem DISKLIST="acd ccd cd ch fd hk hp mcd md ra rb rd rl rx rz \
485 1.27 lukem sd se ss tz uk up vnd wd xd xy"
486 1.27 lukem # DISKLIST="$DISKLIST ct mt st wt"
487 1.15 mrg for i in $DISKLIST; do
488 1.15 mrg egrep "^b.*/${i}[0-9][0-9]*[a-p]$" $LIST >> $TMP1
489 1.15 mrg egrep "^c.*/r${i}[0-9][0-9]*[a-p]$" $LIST >> $TMP1
490 1.15 mrg done
491 1.15 mrg
492 1.15 mrg awk '$3 != "root" || $4 != "operator" || $1 !~ /.rw-r-----/ \
493 1.25 lukem { printf "Disk %s is user %s, group %s, permissions %s.\n", \
494 1.25 lukem $11, $3, $4, $1; }' < $TMP1 > $OUTPUT
495 1.15 mrg if [ -s $OUTPUT ] ; then
496 1.15 mrg printf "\nChecking disk ownership and permissions.\n"
497 1.15 mrg cat $OUTPUT
498 1.9 cgd printf "\n"
499 1.9 cgd fi
500 1.9 cgd
501 1.15 mrg # Display any changes in the device file list.
502 1.20 mycroft egrep '^[bc]' $LIST | sort -k11 > $TMP1
503 1.15 mrg if [ -s $TMP1 ] ; then
504 1.15 mrg CUR=/var/backups/device.current
505 1.15 mrg BACK=/var/backups/device.backup
506 1.15 mrg
507 1.15 mrg if [ -s $CUR ] ; then
508 1.15 mrg if cmp -s $CUR $TMP1 ; then
509 1.15 mrg :
510 1.15 mrg else
511 1.15 mrg > $TMP2
512 1.15 mrg join -111 -211 -v2 $CUR $TMP1 > $OUTPUT
513 1.15 mrg if [ -s $OUTPUT ] ; then
514 1.15 mrg printf "Device additions:\n"
515 1.15 mrg tee -a $TMP2 < $OUTPUT
516 1.15 mrg printf "\n"
517 1.15 mrg fi
518 1.15 mrg
519 1.15 mrg join -111 -211 -v1 $CUR $TMP1 > $OUTPUT
520 1.15 mrg if [ -s $OUTPUT ] ; then
521 1.15 mrg printf "Device deletions:\n"
522 1.15 mrg tee -a $TMP2 < $OUTPUT
523 1.15 mrg printf "\n"
524 1.15 mrg fi
525 1.15 mrg
526 1.27 lukem # Report any block device change. Ignore
527 1.27 lukem # character devices, only the name is
528 1.27 lukem # significant.
529 1.15 mrg cat $TMP2 $CUR $TMP1 | \
530 1.27 lukem sed -e '/^c/d' | \
531 1.27 lukem sort -k11 | \
532 1.27 lukem sed -e 's/[ ][ ]*/ /g' | \
533 1.27 lukem uniq -u > $OUTPUT
534 1.15 mrg if [ -s $OUTPUT ] ; then
535 1.15 mrg printf "Block device changes:\n"
536 1.15 mrg column -t $OUTPUT
537 1.15 mrg printf "\n"
538 1.15 mrg fi
539 1.9 cgd
540 1.15 mrg cp $CUR $BACK
541 1.15 mrg cp $TMP1 $CUR
542 1.9 cgd fi
543 1.15 mrg else
544 1.15 mrg printf "Device additions:\n"
545 1.15 mrg column -t $TMP1
546 1.15 mrg printf "\n"
547 1.9 cgd cp $TMP1 $CUR
548 1.9 cgd fi
549 1.9 cgd fi
550 1.9 cgd fi
551 1.9 cgd
552 1.9 cgd # Check special files.
553 1.9 cgd # Check system binaries.
554 1.9 cgd #
555 1.9 cgd # Create the mtree tree specifications using:
556 1.9 cgd #
557 1.9 cgd # mtree -cx -pDIR -kcksum,gid,mode,nlink,size,link,time,uid > DIR.secure
558 1.16 mikel # chown root.wheel DIR.secure
559 1.16 mikel # chmod 600 DIR.secure
560 1.9 cgd #
561 1.9 cgd # Note, this is not complete protection against Trojan horsed binaries, as
562 1.9 cgd # the hacker can modify the tree specification to match the replaced binary.
563 1.9 cgd # For details on really protecting yourself against modified binaries, see
564 1.9 cgd # the mtree(8) manual page.
565 1.17 mycroft if [ "$check_mtree" = YES ]; then
566 1.9 cgd mtree -e -p / -f /etc/mtree/special > $OUTPUT
567 1.15 mrg if [ -s $OUTPUT ]; then
568 1.9 cgd printf "\nChecking special files and directories.\n"
569 1.9 cgd cat $OUTPUT
570 1.9 cgd fi
571 1.9 cgd
572 1.9 cgd > $OUTPUT
573 1.16 mikel for file in /etc/mtree/*.secure; do
574 1.16 mikel [ $file = '/etc/mtree/*.secure' ] && continue
575 1.9 cgd tree=`sed -n -e '3s/.* //p' -e 3q $file`
576 1.9 cgd mtree -f $file -p $tree > $TMP1
577 1.9 cgd if [ -s $TMP1 ]; then
578 1.9 cgd printf "\nChecking $tree:\n" >> $OUTPUT
579 1.9 cgd cat $TMP1 >> $OUTPUT
580 1.9 cgd fi
581 1.9 cgd done
582 1.15 mrg if [ -s $OUTPUT ]; then
583 1.9 cgd printf "\nChecking system binaries:\n"
584 1.9 cgd cat $OUTPUT
585 1.9 cgd fi
586 1.9 cgd fi
587 1.9 cgd
588 1.9 cgd # List of files that get backed up and checked for any modifications. Each
589 1.9 cgd # file is expected to have two backups, /var/backups/file.{current,backup}.
590 1.9 cgd # Any changes cause the files to rotate.
591 1.17 mycroft if [ "$check_changelist" = YES ] && [ -s /etc/changelist ] ; then
592 1.27 lukem for file in `egrep -v "^#|$MP" /etc/changelist`; do
593 1.9 cgd CUR=/var/backups/`basename $file`.current
594 1.9 cgd BACK=/var/backups/`basename $file`.backup
595 1.9 cgd if [ -s $file ]; then
596 1.9 cgd if [ -s $CUR ] ; then
597 1.9 cgd diff $CUR $file > $OUTPUT
598 1.9 cgd if [ -s $OUTPUT ] ; then
599 1.9 cgd printf "\n======\n%s diffs (OLD < > NEW)\n======\n" $file
600 1.9 cgd cat $OUTPUT
601 1.9 cgd cp -p $CUR $BACK
602 1.9 cgd cp -p $file $CUR
603 1.9 cgd chown root.wheel $CUR $BACK
604 1.9 cgd fi
605 1.9 cgd else
606 1.9 cgd cp -p $file $CUR
607 1.9 cgd chown root.wheel $CUR
608 1.9 cgd fi
609 1.9 cgd fi
610 1.9 cgd done
611 1.9 cgd fi
612