背景知识:
- 《Perl读取wtmpx日志文件》;
- logger命令;
- Syslog日志;
- crontab命令;
参考书籍:
- 《Perl网络编程》
求助:
- Sys::Syslog模块处理系统日志编译警告:your vendor has not defined the Sys::Syslog macro _PATH_LOG...
求各位大大解惑,不胜感激。
源码如下:
#!/usr/bin/perl -w ######################################################################################## # 文件:wtmpx2.pl # 功能:从wtmpx日志里找出最近登录信息写到系统日志里; # 作者:半点闲 # 时间:2012-11-11 11:55 光棍节快乐 # 系统:SCO_SV scosysv 3.2 5.0.6 i386 Perl5.6.0 built for i486-pc-sco3.2v5.0 # 说明:所使用的系统日志功能很弱无法提供登录到系统用户的信息,结合cron定时执行本程序,将提取到 # 的登录信息写到系统日志里.同时,机房采用"集中日志服务器"统一接收系统发送到远端日志进行集中分 # 析处理. # # 进一步说明: # 系统比较陈旧,因是生产用机即不能升级现在又无法更换在,使用Sys::Syslog模块处理系统日志时,# 在Ubuntu+Perl5.14正常的代码,在本机上无法编辑通过提示: # your vendor has not defined the Sys::Syslog macro _PATH_LOG... # <<Perl网络编程>>书中找到一段话:在Perl5.6之前,为了运行这个模块需要syslog.ph头文件,# 但这个文件不和Perl发布版一起提供,需要使用h2ph工具手工产生.在使用Sys::Syslog之前应当 # 升级5.6或更高版本。 # 我的Perl版本按书上所说是满足要求的,难道好事都让我遇到了,不解!想起Perl名言"TMOTWTDI" # 日志部分暂时交给shell的logger命令处理. # -------------------------------------------------------------------------------------- # 修改:2012-11-12 # BUG1:时间精度缺失造成重复记录的问题; # BUG语句: # my ($sec,$min,$hour,$mday,$mon,$year_off) = (localtime)[0..5]; # ($sec,$year_off) = (localtime $tv_sec)[0..5]; # 影响语句:next if($first_time >= $tv_time); # 描述:如当前时间为11:00:00用做数字写入文件时为1100,此时,wtmpx文件中若有登录时间为10:01:01 # 将造成(1100>=100101)返回假值. # 更正:全部以字符方式运算 # $sec = sprintf "%02d",$sec; #不足2位补0 # $min = sprintf "%02d",$min; # $hour = sprintf "%02d",$hour; # 同时修改下述语句: # next if($current_date ne $tv_date); # next if($first_time ge $tv_time); ######################################################################################## use strict; $SIG {__WARN__} = \&log_warn; sub log_warn(){ #warn信息也写到日志里; system "echo '@_' | logger -it wtmpx -p auth.info"; } my $wtmpx_file = '/var/adm/wtmpx'; my $first_file = "/var/adm/first"; #记录前一次查询的时间 my $template = 'A32 A4 A32 s s s s l l l x20 s Z257 x';#ScoUnix5模版 my $recordsize = length( pack( $template,() ) ); my ($sec,$year_off) = (localtime)[0..5]; my $current_date = $year_off + 1900 . $mon + 1 . $mday; $sec = sprintf "%02d",$sec; #不足2位补0 $min = sprintf "%02d",$min; $hour = sprintf "%02d",$hour; my $session = open FirsT_FILE,'+<',$first_file or warn "Unable to open $first_file:$!\n"; my $first_time; #前次查询的时间 if ($session){ $first_time = <FirsT_FILE>; #获取先前的时间 seek FirsT_FILE,0; #移到文件头 print FirsT_FILE "$hour$min$sec"; close FirsT_FILE or warn "Unable to close $first_file:$!\n"; } else { $first_time = "$hour$min$sec"; #使用当前时间 $session = open FirsT_FILE,'>',$first_file or warn "err2:Unable to open $first_file:$!\n"; if ($session){ print FirsT_FILE $first_time; close FirsT_FILE or warn "err2:Unable to close $first_file:$!\n"; } } open WTMP,'<',$wtmpx_file or die "Unable to open wtmpx:$!\n"; my ($ut_user,$ut_id,$ut_line,$ut_pid,$ut_type,$ut_e_termination,$ut_e_exit,$tv_sec,$tv_usec,$ut_session,$ut_syslen,$ut_host) = (); my $record; while( read( WTMP,$record,$recordsize ) ) { ($ut_user,$ut_host) = unpack( $template,$record ); next if $ut_type == 8; #忽略退出的用户 ($sec,$year_off) = (localtime $tv_sec)[0..5]; my $tv_date = $year_off + 1900 . $mon + 1 . $mday; $sec = sprintf "%02d",$sec; $min = sprintf "%02d",$min; $hour = sprintf "%02d",$hour; my $tv_time = "$hour$min$sec"; next if($current_date ne $tv_date); #跳过非当前系统日期的记录(当字符串进行比较) next if($first_time ge $tv_time); #跳过前次查询过的记录(此句只能放在日期比较后面) if ($ut_id eq 'ftp'){ $ut_user = "FTP LOGIN $ut_user"; } else { $ut_user = "LOGIN $ut_user"; } my $format_record = "$ut_user:$ut_id:$ut_line:PID:$ut_pid:TYPE:$ut_type:HOST:$ut_host:$tv_date $hour:$min:$sec"; system "echo '$format_record' | logger -it wtmpx -p auth.info"; } close WTMP;
写入Syslog日志效果图:
日志服务器接收效果图:
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。