- 论坛徽章:
- 0
|
- +++++++++++++++++++++
- +file pppoe_sniff.pl+
- +++++++++++++++++++++
- #!/usr/bin/perl
- use strict;
- use NetPacket::Ethernet;
- use Net::Pcap qw(:functions);
- use NetPacket::PPPOEHeader qw(:pppoe_const);
- use NetPacket::PPPOEDiscovery qw(ETH_TYPE_PPPOE_DISCOVERY);
- use constant ETH_TYPE_PPPOE_DISCOVERY => 0x8863;
- use constant ETH_TYPE_PPPOE_SESSION => 0x8864;
- my $bdebug = 0;
- my($dev,$pcap_handle,$error_msg,$error_rtn,
- $net,$mask,
- $filter,$filter_str);
- $dev="eth0";
- $dev=$ARGV[0] if @ARGV==1;
- print "opening device $dev n";
- #get netmask
- $error_rtn=Net::Pcap::lookupnet($dev,$net,$mask,$error_msg);
- die "can not get the net mask of $devn$error_msgn"
- unless $error_rtn != -1;
- $pcap_handle=open_live($dev,1024,1,0,$error_msg);
- die "can not open $dev to capture packets.n$error_msgn"
- unless defined($pcap_handle);
- print "begin capture packets on $devn";
- #setup the capture filter, man tcpdump-expression for more detail info
- #??seems useless
- $filter="port 13";
- $error_rtn=Net::Pcap::compile($pcap_handle,$filter,$filter_str,1,$mask);
- die "failed to compile the filter.n$error_msgn"
- unless $error_rtn != -1;
- $error_rtn=Net::Pcap::setfilter($pcap_handle,$filter);
- die "failed to set the filter.n$error_msgn"
- unless $error_rtn != -1;
- #install the ctrl_c interrupt function to end the loop
- $SIG{"INT"}=&ctrl_c;
- $error_rtn=loop($pcap_handle,-1,&process_packet,"");
- #you may test the return value , -1 on error, -2 if t by pcap_breakloop
- print "loop terminated.n";
- pcap_close($pcap_handle);
- #subroutings
- #ctrl-c process
- sub ctrl_c
- {
- print "ctrl_c pressed";
- breakloop($pcap_handle);
- }
- #callback from pcap to process captured packets.
- sub process_packet
- {
- my($ether, $pppoe);
- my($user_data,$header,$packet)=@_;
- if($bdebug)
- {
- print "................n";
- print "$header->{tv_usec}t$header->{len}t$header->{caplen}n";
- }
- $ether=NetPacket::Ethernet->decode($packet);
- if($bdebug)
- {
- print "0x$ether->{src_mac}t0x$ether->{dest_mac}t";
- printf("0x%04xn",$ether->{type});
- print "n";
- }
- #print "nParese packet...n";
- #dump_ether($ether);
- #process pppoe packet
- if($ether->{type} == ETH_TYPE_PPPOE_DISCOVERY)
- {
- dump_ether($ether);
- print "--------pppoe packet discovery stage----------n";
- $pppoe=NetPacket::PPPOEDiscovery->decode($ether->{data});
- $pppoe->dump();
- print "n";
- }
- else
- {
- if($ether->{type} == ETH_TYPE_PPPOE_SESSION)
- {
- # print "--------pppoe packet session stage---------n" ;
- $pppoe=NetPacket::PPPOEHeader->decode($ether->{data});
- parse_ifis_PPP_PAP($pppoe->{data});
- # $pppoe->dump();
- # print "n";
- }
- }
- #print "-----------------------------------------n";
- }
- sub dump_ether
- {
- my $self=shift;
- print "----------dump ethernet frames info---------n";
- printf("src_mac=%sndest_mac=%sn",
- $self->{src_mac},$self->{dest_mac});
- }
- sub parse_ifis_PPP_PAP
- {
- my $data=shift;
- my($ppp_proto);
- ($ppp_proto,$data)=unpack("na*",$data);
- #printf("ppp_protocol=%04xn",$ppp_proto);
- if ($ppp_proto == 0xc023 )
- {
- my($code,$ident,$len);
- my($user_name_len,$user_name,$user_password_len,$user_password);
- my($pap_reply_len,$pap_reply);
- #this is the PAP protocol
- ($code,$ident,$len,$data)=unpack("CCna*",$data);
- if($code == 0x01)
- {
- print "nauthenticate requestn";
- ($user_name_len,$data)=unpack("Ca*",$data);
- printf("user name length is %dn",$user_name_len);
- ($user_name,$data)=
- unpack("a".$user_name_len."a*",$data);
- printf("user name is %sn",$user_name);
- ($user_password_len,$data)=unpack("Ca*",$data);
- printf("user password length is %dn",$user_password_len);
- ($user_password,$data)=
- unpack("a".$user_password_len."a*",$data);
- printf("user password is %sn",$user_password);
- }
- if($code == 0x02 || $code == 0x03 )
- {
- print "nauthenticate replyn";
- ($pap_reply_len,$data)=unpack("Ca*",$data);
- printf("pap reply length is %dn",$pap_reply_len);
- ($pap_reply,$data)=
- unpack("a".$pap_reply_len."a*",$data);
- printf("pap reply is n%sn",$pap_reply);
- }
- }
- }
- +++++++++++++++++++++++++++++++++
- +file NetPackage::PPPOEHeader.pm+
- +++++++++++++++++++++++++++++++++
- package NetPacket::PPPOEHeader;
- use strict;
- use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS);
- use NetPacket;
- BEGIN {
- $VERSION="0.01";
- @ISA = qw(Exporter NetPacket);
- # Items to export into callers namespace by default
- # (move infrequently used names to @EXPORT_OK below)
- @EXPORT = qw(
- );
- # Other items we are prepared to export if requested
- @EXPORT_OK = qw(PPPOE_CODE_PADI PPPOE_CODE_PADO
- PPPOE_CODE_PADR PPPOE_CODE_PADS
- PPPOE_CODE_PADT
- );
- # Tags:
- %EXPORT_TAGS = (
- ALL => [@EXPORT, @EXPORT_OK],
- pppoe_const => [qw(PPPOE_CODE_PADI PPPOE_CODE_PADO
- PPPOE_CODE_PADR PPPOE_CODE_PADS
- PPPOE_CODE_PADT)]
- );
- }
- use constant PPPOE_CODE_PADI => 0x09;
- use constant PPPOE_CODE_PADO => 0x07;
- use constant PPPOE_CODE_PADR => 0x19;
- use constant PPPOE_CODE_PADS => 0x65;
- use constant PPPOE_CODE_PADT => 0xa7;
- sub decode {
- my $class = shift;
- my($pkt, $parent, @rest) = @_;
- my $self = {};
- # Decode PPPOE Header
- if (defined($pkt)) {
- my $tmp;
- ($tmp,$self->{code},$self->{session_id},
- $self->{pppoe_length},$self->{data})=unpack('CCnna*',$pkt);
- $self->{version}=($tmp&0xf0)>>4;
- $self->{type}=$tmp&0x0f;
- }
- bless $self,$class;
- return $self;
- }
- sub dump
- {
- my $self = shift;
- print "ndump PPPOE Header info ";
- SWITCH: {
- ($self->{code} == PPPOE_CODE_PADI ) && do {
- print "PADIn"; last SWITCH; };
- ($self->{code} == PPPOE_CODE_PADO ) && do {
- print "PADOn"; last SWITCH; };
- ($self->{code} == PPPOE_CODE_PADR ) && do {
- print "PADRn"; last SWITCH; };
- ($self->{code} == PPPOE_CODE_PADS ) && do {
- print "PADSn"; last SWITCH; };
- ($self->{code} == PPPOE_CODE_PADT ) && do {
- print "PADTn"; last SWITCH; };
- };
- printf("version=%dttype=%dtcode=%dn",
- $self->{version},$self->{type},$self->{code});
- printf("session_id=%dtlength=%dn",
- $self->{session_id},$self->{pppoe_length});
- }
- 1;
- ++++++++++++++++++++++++++++++++
- +file NetPacket::PPPOEDiscovery+
- ++++++++++++++++++++++++++++++++
- #!/usr/bin/perl;
- package NetPacket::PPPOEDiscovery;
- use strict;
- use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS);
- use NetPacket;
- use NetPacket::PPPOEHeader;
- use constant ETH_TYPE_PPPOE_DISCOVERY => 0x8863;
- BEGIN {
- $VERSION="0.01";
- @ISA = qw(Exporter NetPacket NetPacket::PPPOEHeader);
- # Items to export into callers namespace by default
- # (move infrequently used names to @EXPORT_OK below)
- @EXPORT = qw(
- );
- # Other items we are prepared to export if requested
- @EXPORT_OK = qw(
- ETH_TYPE_PPPOE_DISCOVERY
- );
- # Tags:
- %EXPORT_TAGS = (
- ALL => [@EXPORT, @EXPORT_OK],
- );
- }
- sub decode {
- my $class = shift;
- my ($pkt, $parent, @rest)=@_;
- my $self;
- # Decode PPPOE Discovery Packet
- if (defined($pkt)) {
- $self = NetPacket::PPPOEHeader::decode(
- "NetPacket::PPPOEDiscovery",$pkt);
- #parse TAG_VALUE
- $self->parse_tag_value($self->{data});
- }
- return $self;
- }
- sub parse_tag_value{
- my ($self,$pkt) = @_;
- my @tags;
- while(defined($pkt))
- {
- my %atag;
- ($atag{tag_type},$atag{tag_length},
- $pkt)=unpack('nna*',$pkt);
- $atag{tag_value}="";
- if($atag{tag_length}>0)
- {
- if($atag{tag_type} == 0x0102 ||
- $atag{tag_type} == 0x0201 ||
- $atag{tag_type} == 0x0202 ||
- $atag{tag_type} == 0x0203 )
- {
- ($atag{tag_value}, $pkt)=
- unpack("a".$atag{tag_length}."a*",$pkt);
- }
- else
- {
- ($atag{tag_value},$pkt)=
- unpack('H'.2*$atag{tag_length}.'a*',$pkt);
- }
- }
- push @tags,%atag;
- }
- $self->{tags}=@tags;
- }
- sub dump
- {
- my $self=shift;
- $self->SUPER::dump();
- print "----PPPOE::Discovery Stage----n";
- printf("tag list:(?)n",@{$self->{tags}});
- foreach my $ref_atag (@{$self->{tags}})
- {
- printf("tag_type=%04xttag_length=%dntag_value=%snn",
- $ref_atag->{tag_type},
- $ref_atag->{tag_length},
- $ref_atag->{tag_value});
- }
- print "--------n";
- }
- 1;
- +++++++++++++++++++++++++++++++++
- +file NetPacket::PPPOESession.pm+
- +++++++++++++++++++++++++++++++++
- #!/usr/bin/perl;
- package NetPacket::PPPOESession;
- use strict;
- use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS);
- use NetPacket;
- use NetPacket::PPPOEHeader;
- use constant ETH_TYPE_PPPOE_SESSION => 0x8864;
- BEGIN {
- $VERSION="0.01";
- @ISA = qw(Exporter NetPacket NetPacket::PPPOEHeader);
- # Items to export into callers namespace by default
- # (move infrequently used names to @EXPORT_OK below)
- @EXPORT = qw(
- );
- # Other items we are prepared to export if requested
- @EXPORT_OK = qw(
- ETH_TYPE_PPPOE_SESSION
- );
- # Tags:
- %EXPORT_TAGS = (
- ALL => [@EXPORT, @EXPORT_OK],
- );
- }
- sub decode {
- my $class = shift;
- my ($pkt, $parent, @rest)=@_;
- my $self;
- # Decode PPPOE Discovery Packet
- if (defined($pkt)) {
- $self = NetPacket::PPPOEHeader::decode(
- "NetPacket::PPPOE:Discovery",$pkt);
- #parse TAG_VALUE
- $self->parse_tag_value($self->{data});
- }
- return $self;
- }
- sub parse_tag_value{
- my ($self,$pkt) = @_;
- my @tags;
- while(defined($pkt))
- {
- my %atag;
- ($atag{tag_type},$atag{tag_length},
- $pkt)=unpack('nna*',$pkt);
- $atag{tag_value}="";
- if($atag{tag_length}>0)
- {
- if($atag{tag_type} == 0x0102 ||
- $atag{tag_type} == 0x0201 ||
- $atag{tag_type} == 0x0202 ||
- $atag{tag_type} == 0x0203 )
- {
- ($atag{tag_value}, $pkt)=
- unpack("a".$atag{tag_length}."a*",$pkt);
- }
- else
- {
- ($atag{tag_value},$pkt)=
- unpack('H'.2*$atag{tag_length}.'a*',$pkt);
- }
- }
- push @tags,%atag;
- }
- $self->{tags}=@tags;
- }
- sub dump
- {
- my $self=shift;
- $self->SUPER::dump();
- print "----PPPOE::Discovery Stage----n";
- printf("tag list:(?)n",@{$self->{tags}});
- foreach my $ref_atag (@{$self->{tags}})
- {
- printf("tag_type=%04xttag_length=%dntag_value=%snn",
- $ref_atag->{tag_type},
- $ref_atag->{tag_length},
- $ref_atag->{tag_value});
- }
- print "--------n";
- }
- 1;
复制代码
[ 本帖最后由 angleeye 于 2005-11-22 22:40 编辑 ] |
|