Poprawny format ramki:
@s = unpack("H6 H2 H6 H12 N (H2n/a*)*", $ramka);No i sam scanner:
#!/usr/bin/perl ############################################################################### # # scan-ubiquiti.pl v2.1.0 # # scan utility for ubiquiti # # 2012-08-24 # dodano rozpoznawanie kodow hardware'u: 'NS3','B2N','BS2' # # 2012-08-22 # poprawiono parsowanie odbieranego pakietu # poprawiono parsowanie wersji software # # 2011-06-11 # przepisano engine na klasyczne sockety # # mindc.net # 2011-03-20 ############################################################################### use strict; use warnings; use Socket; use Time::HiRes qw(gettimeofday); print "scan-ubiquiti.pl v2.0.0 hw ip board sw uptime name ssid -------------------------------------------------------------------------------------------------------- "; my %dev; open my $ph, "-|","ip a"; while ( <$ph> ) { $dev{$2} = $1 if m@\s(\S+)/\d+\s.*(eth\d+)@; } close $ph; my $data = {}; foreach my $saddr ( values %dev ) { my $socket; socket($socket,PF_INET,SOCK_DGRAM,17); setsockopt($socket, SOL_SOCKET, SO_BROADCAST, 1 ); my $sin = sockaddr_in(50122,inet_aton($saddr)); bind($socket,$sin); my $sout = sockaddr_in(10001,INADDR_BROADCAST); send($socket,pack("H8","01000000"),0,$sout); send($socket,pack("H8","01000000"),0,$sout); send($socket,pack("H8","01000000"),0,$sout); close $socket; } my $socket; socket($socket,PF_INET,SOCK_DGRAM,17) or die "socket error - $!"; my $sin = sockaddr_in(50122,INADDR_ANY); bind($socket,$sin); setsockopt($socket, SOL_SOCKET, SO_BROADCAST, 0 ); my $rin = ""; vec($rin,fileno($socket),1) = 1; my $end = gettimeofday() + 3; my $timeout = $end - gettimeofday(); my $i = 0; while ( select(my $rout = $rin,undef,undef,$timeout) ) { $timeout = $end - gettimeofday(); my $rtime = ""; my $his = recv($socket,$rtime,1500,0) || die "recv: $!"; my ($port,$hisaddr) = sockaddr_in($his); next if length($rtime) < 8; #skip self my $o = ubiquiti_header(inet_ntoa($hisaddr),$rtime); if ( not exists($data->{$o->{mac}})) { my $sw = parse_sw($o->{sw}); printf("%3d. %17s %-16s %-16s %-6s %6s %-32s %s\n", ++$i, $o->{mac} || '', $o->{ip} || '', models($o->{board}) || '', $sw->{sw_version} || '', sec2human($o->{uptime}) || '', $o->{name} || '', $o->{ssid} || '' ); } $data->{$o->{mac}}++; } close $socket; print "\n" if keys %$data; exit; sub ubiquiti_header { my $ip = shift; my $frame = shift; my $template = "H6 H2 H6 H12 N (H2n/a*)*"; my @header = unpack($template,$frame); my $signature = shift @header; return undef if $signature ne '010000'; my $t = shift @header; shift @header; my $mac = shift @header; shift @header; my $out = {}; @{$out}{qw(ip mac sw board key uptime ssid)} = ($ip,'','','','',0,''); for ( my $i = 0; $i < @header ; $i += 2 ) { my $type = $header[$i]; my $value = $header[$i+1]; $out->{sw} = $value if $type eq '03'; $out->{board} = $value if $type eq '0c'; $out->{name} = $value if $type eq '0b'; $out->{uptime} = unpack("N",$value) if $type eq '0a'; $out->{ssid} = $value if $type eq '0d'; } $out->{mac} = uc join(":",unpack("(H2)6",pack("H*",$mac))); $out->{frame} = $frame; $out->{structure} = \@header; return $out; } sub sec2human { my $sec = shift; return "" if $sec <= 0; my $w = int($sec / 60 / 60 / 24 / 7); my $d = int($sec / 60 / 60 / 24 % 7); my $h = int($sec / 60 / 60 % 24); my $m = int($sec / 60 % 60); my $s = int($sec % 60); if ( $w ) { return sprintf("%dw%dd",$w,$d); } elsif ( $d ) { return sprintf("%dd%dh",$d,$h); } elsif ( $h ) { return sprintf("%dh%dm",$h,$m); } elsif ( $m ) { return sprintf("%dm%ds",$m,$s); } else { return "${s}s"; } } sub parse_sw { my $sw = shift; return {} unless $sw; my @d = $sw =~ m/(\S{2,3})\.(ar\d+)\.v(\S+)\.(\d{4,5})\.(\d{6})\.(\d{4})/; my $out = { board => $d[0] || '', chipset => uc $d[1] || '', sw_version => $d[2], build => $d[3] || '', date => $d[4] || '', unkn => $d[5] || '' }; return $out; } sub models { my $m = shift; return 'NanoBridge M5' if $m eq 'NB5'; return 'WispStation5' if $m eq 'MS5'; return 'Rocket M5' if $m eq 'R5N'; return 'AirGrid M5' if $m eq 'AG5'; return 'NanoStation M3' if $m eq 'NS3'; return 'Bullet M2' if $m eq 'B2N'; return 'Bullet 2' if $m eq 'BS2'; return $m; };