Repository URL to install this package:
#!/usr/bin/env perl
#
# Copyright 2006-2016 Roy Hills
#
# This file is part of arp-scan.
#
# arp-scan is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# arp-scan is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with arp-scan. If not, see <http://www.gnu.org/licenses/>.
#
# arp-fingerprint -- Perl script to fingerprint system with arp-scan
#
# Author: Roy Hills
# Date: 30th May 2006
#
# This script uses arp-scan to fingerprint the operating system on the
# specified target.
#
# It sends various different ARP packets to the target, and records which
# ones it responds to. From this, it constructs a fingerprint string
# which is used to match against a hash containing known fingerprints.
#
use warnings;
use strict;
use Getopt::Std;
#
sub get_localnet($);
#
my $arpscan="arp-scan -q -r 1";
#
# Hash of known fingerprints
#
# These fingerprints were observed on:
#
# FreeBSD 10.3 FreeBSD 10.3 amd64 on VMware
# FreeBSD 9.1 FreeBSD 9.1 i386 on VMware
# FreeBSD 8.2 FreeBSD 8.2 i386 on VMware
# FreeBSD 7.0 FreeBSD 7.0 i386 on VMware
# FreeBSD 5.3 FreeBSD 5.3 i386 on VMware
# FreeBSD 4.3 FreeBSD 4.3 i386 on VMware
# DragonflyBSD 2.0 Dragonfly BSD 2.0.0 i386 on VMware
# DragonflyBSD 3.0 Dragonfly BSD 3.0.2 i386 on VMware
# DragonflyBSD 3.2 Dragonfly BSD 3.2.2 amd64 on VMware
# DragonflyBSD 4.6 Dragonfly BSD 4.6.0 amd64 on VMware
# Win 3.11 Windows for Workgroups 3.11/DOS 6.22 on VMware
# 95 Windows 95 OSR2 on VMware
# Win98 Windows 98 SE on VMware
# WinME Windows ME on VMware
# Windows7 Windows 7 Professional 6.1.7600 Build 7600 on Dell Vostro 220
# Windows8 Windows 8 Pro x64 6.2.9200 Build 9200 on VMware
# Windows10 Windows 10 Pro 10.0.14393 Build 14393 on VMware
# NT 3.51 Windows NT Server 3.51 SP0 on VMware
# NT4 Windows NT Workstation 4.0 SP6a on Pentium
# 2000 Windows 2000
# XP Windows XP Professional SP2 on Intel P4
# 2003 Windows 2003 Server SP1 on Intel P4
# Vista Windows Vista Beta 2 Build 5384 on VMware
# Vista Windows Vista SP1 Build 6001 on Dell Inspiron
# 2008 Windows 2008 Server Beta on i386
# Linux 2.0 Linux 2.0.29 on VMware (debian 1.3.1)
# Linux 2.2 Linux 2.2.19 on VMware (debian potato)
# Linux 2.4 Linux 2.4.29 on Intel P3 (debian sarge)
# Linux 2.6 Linux 2.6.15.7 i686 on Intel P3 (debian sarge)
# Linux 2.6 Kindle 3.1 on Amazon Kindle 3
# Linux 2.6 Linux 2.6.32.60 x86_64 on VMware (debian squeeze)
# Linux 3.2 Linux 3.2.0 686 on VMware (debian wheezy)
# Linux 3.8 Linux 3.8.8 x86_64 on VMware (fedora 17)
# Linux 4.0 Linux 4.0.6 x86_64 on VMware (fedora 22)
# Linux 4.6 Linux 4.6.7 x86_64 on VMware (fedora 24)
# Cisco IOS IOS 11.2(17) on Cisco 2503
# Cisco IOS IOS 11.3(11b)T2 on Cisco 2503
# Cisco IOS IOS 12.0(8) on Cisco 1601
# Cisco IOS IOS 12.1(27b) on Cisco 2621
# Cisco IOS IOS 12.2(32) on Cisco 1603
# Cisco IOS IOS 12.3(15) on Cisco 2503
# Cisco IOS IOS 12.4(3) on Cisco 2811
# Cisco IOS IOS 12.4(24)T1 on Cisco 1841
# Cisco IOS IOS 15.0(1)M on Cisco 7206 (dynamips)
# Solaris 2.5.1 Solaris 2.5.1 (SPARC) on Sun SPARCstation 20
# Solaris 2.6 Solaris 2.6 (SPARC) on Sun Ultra 5
# Solaris 7 Solaris 7 (x86) on VMware
# Solaris 8 Solaris 8 (SPARC) on Sun Ultra 5 (64 bit)
# Solaris 9 Solaris 9 (SPARC) on Sun Ultra 5 (64 bit)
# Solaris 10 Solaris 10 (x86) on VMware
# ScreenOS 5.0 Juniper ScreenOS 5.0.0r9 on NetScreen 5XP
# ScreenOS 5.1 Juniper ScreenOS 5.1.0r1.0 on NetScreen 5GT
# ScreenOS 5.3 Juniper ScreenOS 5.3.0r4.0 on NetScreen 5GT
# ScreenOS 5.4 Juniper ScreenOS 5.4.0r1.0 on NetScreen 5GT
# ScreenOS 5.4 Juniper ScreenOS 5.4.0r22.0 on NetScreen 5GT
# ScreenOS 6.2 Juniper ScreenOS 6.2.0r12.0 on Juniper SSG5
# MacOS 10.4 MacOS 10.4.6 on powerbook G4
# MacOS 10.3 MacOS 10.3.9 on imac G3
# IRIX 6.5 IRIX64 IRIS 6.5 05190004 IP30 on SGI Octane
# SCO OS 5.0.7 SCO OpenServer 5.0.7 on VMware
# 2.11BSD 2.11BSD patch level 431 on PDP-11/73 (SIMH simulated)
# 4.3BSD 4.3BSD (Quasijarus0c) on MicroVAX 3000 (SIMH simulated)
# OpenBSD 3.1 OpenBSD 3.1 i386 on VMware
# OpenBSD 3.9 OpenBSD 3.9 i386 on VMware
# OpenBSD 4.8 OpenBSD 4.8 i386 on VMware
# OpenBSD 5.1 OpenBSD 5.1 amd64 on VMware
# OpenBSD 5.9 OpenBSD 5.9 amd64 on VMware
# NetBSD 2.0.2 NetBSD 2.0.2 i386 on VMware
# NetBSD 4.0 NetBSD 4.0 i386 on VMware
# NetBSD 5.1 NetBSD 5.1.2 i386 on VMware
# NetBSD 6.0 NetBSD 6.0.1 amd64 on VMware
# NetBSD 7.0 NetBSD 7.0.1 amd64 on VMware
# IPSO 3.2.1 IPSO 3.2.1-fcs1 on Nokia VPN 210
# Netware 6.5 Novell NetWare 6.5 on VMware
# HP-UX 11 HP-UX B.11.00 A 9000/712 (PA-RISC)
# PIX OS PIX OS (unknown vsn) on Cisco PIX 525
# PIX OS 4.4 PIX OS 4.4(4) on Cisco PIX 520
# PIX OS 5.1 PIX OS 5.1(2) on Cisco PIX 520
# PIX OS 5.2 PIX OS 5.2(9) on Cisco PIX 520
# PIX OS 5.3 PIX OS 5.3(2) on Cisco PIX 520
# PIX OS 6.0 PIX OS 6.0(4) on Cisco PIX 520
# PIX OS 6.1 PIX OS 6.1(5) on Cisco PIX 520
# PIX OS 6.2 PIX OS 6.2(4) on Cisco PIX 520
# PIX OS 6.3 PIX OS 6.3(5) on Cisco PIX 520
# PIX OS 7.0(1) PIX OS 7.0(1) on Cisco PIX 515E
# PIX OS 7.0(2) PIX OS 7.0(2) on Cisco PIX 515E
# PIX OS 7.0(4) PIX OS 7.0(4) on Cisco PIX 515E
# PIX OS 7.0(6) PIX OS 7.0(6) on Cisco PIX 515E
# PIX OS 7.1 PIX OS 7.1(1) on Cisco PIX 515E
# PIX OS 7.2 PIX OS 7.2(1) on Cisco PIX 515E
# PIX OS 8.0 PIX OS 8.0(2) on Cisco PIX 515E
# Minix 3 Minix 3 1.2a on VMware
# Nortel Contivity 6.00 Nortel Contivity V06_00 (VxWorks based)
# Nortel Contivity 6.05 Nortel Contivity V06_05.135
# AIX 4.3 IBM AIX Version 4.3 on RS/6000 7043-260
# AIX 5.3 IBM AIX Version 5.3 on RS/6000 7043-260
# Cisco VPN Concentrator 4.7 Cisco VPN Concentrator 3030 4.7.2E
# Cisco IP Phone 79xx SIP 5.x,6.x,7.x 7940 SIP firmware version 5.3
# Cisco IP Phone 79xx SIP 5.x,6.x,7.x 7940 SIP firmware version 6.3
# Cisco IP Phone 79xx SIP 5.x,6.x,7.x 7940 SIP firmware version 7.5
# Cisco IP Phone 79xx SIP 8.x 7940 SIP firmware version 8.6
# Catalyst 1900 Cisco Catalyst 1900 V9.00.03 Standard Edition
# Catalyst IOS 12.2 Cisco Catalyst 3550-48 running IOS 12.2(35)SE
# Catalyst IOS 12.0 Cisco Catalyst 2924-XL running IOS 12.0(5)WC17
# Catalyst IOS 12.1 Cisco Catalyst 3550-48 running IOS 12.1(11)EA1a SMI
# FortiOS 3.00 FortiGate 100A running FortiOS 3.00,build0406,070126
# Plan9 Plan9 release 4 on VMware
# Blackberry OS Blackberry OS v5.0.0.681 on Blackberry 8900
# GNU/Hurd Debian GNU/Hurd (GNU-Mach 1.3.99/Hurd-0.3) on VMware
# BeOS BeOS 5.0.3 PE Max on VMware
# RiscOS 5.19 RiscOS 5.19 on Raspberry Pi
# WIZnet W5100 WIZnet W5100 on Ethernet chip on Arduino Ethernet shield
# Android 4.1 Android 4.1.2 on Samsung Galaxy S3 Mini (wifi)
# Android 4.4 Android 4.4.2 on Google Nexus 7 (wifi)
#
my %fp_hash = (
'11110100000' => 'FreeBSD 5.3, 7.0, 8.2, 9.1, 10.3, DragonflyBSD 2.0, 3.0, 3.2, 4.6, Win98, WinME, NT4, 2000, XP, 2003, Catalyst IOS 12.0, 12.1, 12.2, FortiOS 3.00',
'01000100000' => 'Linux 2.2, 2.4, 2.6',
'01010100000' => 'Linux 2.2, 2.4, 2.6, 3.2, 3.8, 4.0, 4.6, Vista, 2008, Windows7, Windows8, Windows10', # Linux only if non-local IP is routed
'00000100000' => 'Cisco IOS 11.2, 11.3, 12.0, 12.1, 12.2, 12.3, 12.4, 15.0',
'11110110000' => 'Solaris 2.5.1, 2.6, 7, 8, 9, 10, HP-UX 11, NetBSD 6.0, 7.0',
'01000111111' => 'ScreenOS 5.0, 5.1, 5.3, 5.4, 6.2',
'11110000000' => 'Linux 2.0, MacOS 10.4, IPSO 3.2.1, Minix 3, Cisco VPN Concentrator 4.7, Catalyst 1900, BeOS, WIZnet W5100',
'11110100011' => 'MacOS 10.3, FreeBSD 4.3, IRIX 6.5, AIX 4.3, AIX 5.3',
'10010100011' => 'SCO OS 5.0.7',
'10110100000' => 'Win 3.11, 95, NT 3.51',
'11110000011' => '2.11BSD, 4.3BSD, OpenBSD 3.1, 3.9, 4.8, 5.1, 5.9, Nortel Contivity 6.00, 6.05, RiscOS 5.19',
'10110110000' => 'NetBSD 2.0.2, 4.0, 5.1',
'10110111111' => 'PIX OS 4.4, 5.1, 5.2, 5.3, Android 4.1',
'11110111111' => 'PIX OS 6.0, 6.1, 6.2, ScreenOS 5.0 (transparent), Plan9, Blackberry OS',
'00010110011' => 'PIX OS 6.3, 7.0(1), 7.0(2)',
'01010110011' => 'PIX OS 7.0(4)-7.0(6), 7.1, 7.2, 8.0',
'00000110000' => 'Netware 6.5',
'00010100000' => 'Unknown 1', # 14805 79.253 Cisco
'00000110011' => 'Cisco IP Phone 79xx SIP 5.x,6.x,7.x',
'11110110011' => 'Cisco IP Phone 79xx SIP 8.x', # Also 14805 63.11 Fujitsu Siemens
'01010000000' => 'GNU/Hurd, Android 4.4',
);
#
my $usage =
qq/Usage: arp-fingerprint [options] <target>
Fingerprint the target system using arp-scan.
'options' is one or more of:
-h Display this usage message.
-v Give verbose progress messages.
-o <option-string> Pass specified options to arp-scan
-l Fingerprint all targets in the local net.
/;
my %opts;
my $user_opts="";
my $verbose;
my $fingerprint="";
my $fp_name;
my @targets;
my $target;
#
# Process options
#
die "$usage\n" unless getopts('hlvo:',\%opts);
if ($opts{h}) {
print "$usage\n";
exit(0);
}
$verbose=$opts{v} ? 1 : 0;
if ($opts{o}) {
$user_opts = $opts{o};
}
#If we're working in localnet mode, we don't need arguments
if ($#ARGV != 0 && !$opts{l}) {
die "$usage\n";
}
if ($opts{l}) {
@targets=get_localnet($user_opts);
} else {
@targets=@ARGV;
}
for $target (@targets) {
$fingerprint="";
#
# Check that the target is not an IP range or network.
#
if ($target =~ /\d+\.\d+\.\d+\.\d+-\d+\.\d+\.\d+\.\d+/ ||
$target =~ /\d+\.\d+\.\d+\.\d+\/\d+/ ||
$target =~ /\d+\.\d+\.\d+\.\d+:\d+\.\d+\.\d+\.\d+/) {
die "argument must be a single IP address or hostname\n";
}
#
# Check that the system responds to an arp-scan with no options.
# If it does, then fingerprint the target.
#
if (&fp("","$target") eq "1") {
# 1: source protocol address = localhost
$fingerprint .= &fp("--arpspa=127.0.0.1","$target");
# 2: source protocol address = zero
$fingerprint .= &fp("--arpspa=0.0.0.0","$target");
# 3: source protocol address = broadcast
$fingerprint .= &fp("--arpspa=255.255.255.255","$target");
# 4: source protocol address = non local (network 1 is reserved)
$fingerprint .= &fp("--arpspa=1.0.0.1","$target"); # Non-local source IP
# 5: invalid arp opcode
$fingerprint .= &fp("--arpop=255","$target");
# 6: arp hardware type = IEEE_802.2
$fingerprint .= &fp("--arphrd=6","$target");
# 7: invalid arp hardware type
$fingerprint .= &fp("--arphrd=255","$target");
# 8: invalid arp protocol type
$fingerprint .= &fp("--arppro=0xffff","$target");
# 9: arp protocol type = Novell IPX
$fingerprint .= &fp("--arppro=0x8137","$target");
# 10: invalid protocol address length
$fingerprint .= &fp("--arppln=6","$target");
# 11: Invalid hardware address length
$fingerprint .= &fp("--arphln=8","$target");
#
if (defined $fp_hash{$fingerprint}) {
$fp_name = "$fp_hash{$fingerprint}";
} else {
$fp_name = "UNKNOWN";
}
print "$target\t$fingerprint\t$fp_name\n";
} else {
print "$target\tNo Response\n";
}
}
#
# Scan the specified IP address with arp-scan using the given options.
# Return "1" if the target responds, or "0" if it does not respond.
#
sub fp ($$) {
my $ip;
my $options;
my $response = "0";
($options, $ip) = @_;
open(ARPSCAN, "$arpscan $user_opts $options $ip |") || die "arp-scan failed";
while (<ARPSCAN>) {
if (/^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+\t/) {
$response = "1";
last;
}
}
close(ARPSCAN);
if ($verbose && $options ne "") {
if ($response) {
print "$options\tYes\n";
} else {
print "$options\tNo\n";
}
}
return $response;
}
#
# use -l flag on arp-scan to collect all IPs in the local network
#
sub get_localnet($) {
my $user_opts = $_[0];
my @targets;
open(ARPSCAN, "$arpscan $user_opts -l |") || die "arp-scan failed";
while (<ARPSCAN>) {
if (/^([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+)\t/) {
push @targets, $1;
}
}
close(ARPSCAN);
die "parse of arp-scan failed" unless @targets;
return @targets;
}