一天一客户打电话说其公司的某一个共享文件夹完全不见,赶到客户处,经过分析,发现是因为某部门的同事不小心将之移动到其它的位置,把客户给吓得半 死。后来同其商量,为了解决此种,以及出现问题之后可以快速找出是谁进行的误操作(比如是谁什么时间删除了文件,复制了文件等),以追究责任。决定 从两方面下手,第一,实现对每个共享及文件详细的ACL控制,虽然麻烦点,但能够有效的预防因为误操作而造成损失。第二,就是对samba决定启用日志管 理。

客户处环境:
操作系统:CentOS 5.3 Linux filesvr01 2.6.18-128.el5 #1 SMP Wed Jan 21 10:41:14 EST 2009 x86_64 x86_64 x86_64 GNU/Linux
Samba版本:Samba version 3.0.33-3.7.el5
Samba认让:使用winbind,通过ad认证

1、决定采用系统自带的审核功能,启用审核之后,发现日志中所得之信息不是想要的,此想法被否决。

2、所以只能通过samba入手,仔细看其配置选项,发现加入log level=3可以启用比较详细的日志选项,但其日志仍然不是我们所需要。

3、 再仔细在samba.org网站查找其实配置指南,发现samba支持一个vfs功能(注,需要3.0以上的samba)。通过此vfs功能,我们可以对 samba实现文件审核,扩展审核,防病毒,误删除恢复,影子镜像等功能。正是我们所需要功能。vfs详细介绍,请参考http://www.samba.org/samba/docs/man/Samba-HOWTO-Collection/VFS.html。加入相应的参数在smb.conf中
syslog=2 使用此选项是因为vfs会向/var/log/messages中写入日志,但为了更好的区分vfs产生的日志,所以将vfs写入messages中的日志等级改为2,对应于系统的notice级别,以便于单独处理。
log level =0 vfs:10

4、修改/etc/syslog.conf,全smaba产生的2级别的日志单独记入某个文件
修改此行
*.info;mail.none;authpriv.none;cron.none /var/log/messages

*.!notice;mail.none;authpriv.none;cron.none; /var/log/messages 使notice级别的日志不再记入messages文件中
另外再增加
*.=notice -/var/log/sysnotice.log 让notice级别的日志记入sysnotice.log中

5、重启相应的服务,此时相应的日志会记入日志文件中。

service syslog restart

service smb reload

6、查看/var/log/sysnotic.log发现已经有相应的日志记入。虽然有日志写入,但是并不能找到是那个用户在访问,只能找到是那个进程访问。

Jan 9 17:05:22 filesvr01 smbd_audit[4806]: opendir 4DGame/Jokul/Finalp_w_picpaths/RendImages/VFX
Jan 9 17:05:22 filesvr01 smbd_audit[4806]: opendir 4DGame/Jokul/Project/p_w_picpaths/zjn
Jan 9 17:05:22 filesvr01 smbd_audit[14508]: opendir 4DGame/Mushroom/Project/scenes/Assets/Sets/Mg_C_grp
Jan 9 17:05:22 filesvr01 smbd_audit[14508]: opendir 4DGame/Mushroom/Project/scenes/Shots/Shot01/Animation
Jan 9 17:05:22 filesvr01 smbd_audit[12985]: opendir 4DGame/Jokul/Project/p_w_picpaths/Tree_Shadow/Tree_D_Shadow

7、通过smbstatus可以得到smb进程所对应的用户,结合此信息,然后通过脚本分析日志文件就可以得到详细的日志文件了。

[root@filesvr01 2010-01-09]# smbstatus -p

Samba version 3.0.33-3.7.el5
PID Username Group Machine
——————————————————————-
4339 zoujn domain users 192.168.2.41 (192.168.2.41)
14508 renclient domain users xw4600-cam (192.168.2.36)
14294 renclient domain users 192.168.2.34 (192.168.2.34)
4429 zhijq domain users 192.168.2.51 (192.168.2.51)
24118 zengwc domain users 192.168.2.52 (192.168.2.52)
8360 renclient domain users 192.168.2.64 (192.168.2.64)

8、将脚本加入cron计划任务中,定时执行。
=============================================
以上为解决问题的思路,当然其中还有很多问题需要考虑

以下为我写好的脚本文件,大家可以参考参考

===========================================

脚本一:CeckSmbPid 得到当前Samba进程号所对应的用户名
#!/bin/bash
#Author:MingPeng
#WriteDate:2010/01
#Programe name:CheckSMBPid
#Ouput File:/var/log/samba/#DATE#-pid.log

IFS=””
OutPutLog=”/var/log/messages”
OutPutDir=”/var/log/samba/smbpid/”
OutPutFile=$OutPutDir`date +%F`”-pid.log”
TmpPutFile=$OutPutDir”tmp.”$RANDOM”.log”
FirstPidFile=$OutPutDir”firstpidfile”

if [ ! -d $OutPutDir ]; then
mkdir -p $OutPutDir > /dev/null 2>/dev/null
if [ $? -ne 0 ]; then
echo `date`” Create $OutPutDir direcotry was failed!” >> $OutPutLog
exit 1
fi
fi
if [ `which smbstatus > /dev/null 2>/dev/null` ];then
echo `date`” Can’t find smbstatus!” >> $OutPutLog
exit 2
else
if [ ! -f $FirstPidFile ];then
smbstatus -p | sed ’1,4d;/renclient/ d;/domain computers/ d;s/domain users/domain-users/g’ | sort -nk1 > $FirstPidFile
echo `date`” This program was first run,create the first pid file!” >> $OutPutLog
exit 0
fi
smbstatus -p | sed ’1,4d;/renclient/ d;/domain computers/ d;s/domain users/domain-users/g’ | sort -nk1 > $TmpPutFile
if [ $? -ne 0 ];then
echo `date`” Output tmp log failed!” >> $OutPutLog
exit 3
fi
fi
if [ -f $FirstPidFile -a -f $TmpPutFile ];then
cat $FirstPidFile >> $TmpPutFile
sort -nk1 $TmpPutFile | uniq > $OutPutFile
cp $OutPutFile $FirstPidFile
rm -rf $TmpPutFile
#echo `date`” Output Samba Pid was successed!” >> $OutPutLog
fi

脚本二:ProcessSMBLog 处理日志

#!/bin/bash
#Author:MingPeng
#WriteDate:2010/01
#ProgramName:ProcessSMBLog
#OutPutFile:/var/log/samba/smblog/$DATE$/$USER$.log
#OutPutFile:/var/log/samba/smblog/$DATE$/Orig-$DATE$.log

IFS=””
OrigLogFile=”/var/log/sysnotice.log”
OutPutLogDestDir=”/var/log/samba/smblog/”`date +%F`|
OutPutOrigSmbLog=$OutPutLogDestDir”/Orig-”`date +%F`.log
OutPutLog=”/var/log/samba/smblog/process”`date +%F`”.log”

TmpLogFile=”/tmp/tmp.$RANDOM.log”
SmbPidFile=”/var/log/samba/smbpid/”`date +%F`”-pid.log”
SvrName=”filesvr01″
SmbPid=””
SmbUser=””
SmbMachine=””
SmbIP=””
SearchStr=””
ProcessLines=””

if [ ! -d $OutPutLogDestDir ];then
mkdir -p $OutPutLogDestDir > /dev/null 2>/dev/null
if [ $? -ne 0 ];then
echo `date`” Create $OutPutLogDestDir direcotry was failed!” >> $OutPutLog
exit 1
fi
fi

if [ ! -f $OrigLogFile ];then
echo `date`” Open the orig log file was failed!” >> $OutPutLog
exit 2
fi

ProcessLines=`wc -l $OrigLogFile | cut -d’ ‘ -f1`
if [ ! -f $OutPutOrigSmbLog ];then
sed “$ProcessLines q” $OrigLogFile | grep “smbd_audit” > $OutPutOrigSmbLog
if [ $? -ne 0 ];then
echo `date`” Output the orig log $OutPutOrigSmbLog was failed!” >> $OutPutLog
exit 3
fi
else
OutPutOrigSmbLog=$OutPutLogDestDir”/Orig-”`date +%F`”.$RANDOM.log”
sed “$ProcessLines q” $OrigLogFile | grep “smbd_audit” > $OutPutOrigSmbLog
if [ $? -ne 0 ];then
echo `date`” Output the orig log $OutPutOrigSmbLog was failed!” >> $OutPutLog
exit 3
fi
fi

if [ ! -f $SmbPidFile ];then
echo `date`” Cann’t find the Smaba Pid Files!” >> $OutPutLog
exit 4
fi

while read -r line
do
SmbPid=$(echo $line | awk ‘{print $1}’)
SmbUser=$(echo $line | awk ‘{print $2}’)
SmbMachine=$(echo $line | awk ‘{print $4}’)
SmbIP=$(echo $line | awk ‘{print $5}’)
SearchStr=”smbd_audit\\["$SmbPid"\\]”
echo `date`” Process $SmbUser…” >> $OutPutLog
grep $SearchStr $OutPutOrigSmbLog | sort | uniq | sed “s/$SvrName/User:$SmbUser/g;s/$SearchStr/on machine $SmbMachine$SmbIP with process $SmbPid/g” >> $OutPutLogDestDir/$SmbUser.log
if [ $? -eq 0 ];then
echo `date`” Process $SmbUser Done!” >> $OutPutLog
else
echo `date`” Process $SmbUser Failed!” >> $OutPutLog
fi
done < $SmbPidFile
sed -i "1,$ProcessLines s/smbd_audit/_Processed_smbd_audit/" $OrigLogFile
sed -i "/_Processed_smbd_audit/d" $OrigLogFile

if [ $? -ne 0 ];then
echo `date`" Clear samba log successed!" >> $OutPutLog
fi