royhills / arp-scan

The ARP Scanner
GNU General Public License v3.0
977 stars 154 forks source link

Feature Request: Output options: Add sorting #156

Open gspannu opened 1 year ago

gspannu commented 1 year ago

Feature Request:

Would it be possible to sort the output by IP address? Or to make it really useful, have an option to sort by fieldname?

As an example; something like...

Sort by IP address... arp-scan --resolve --format='${ip;-16}| ${mac} | ${name;20}' --sort='${ip}' --localnet

Sort by MAC address... arp-scan --resolve --format='${ip;-16}| ${mac} | ${name;20}' --sort='${mac}' --localnet

Sort by Vendor name (but in reverse) arp-scan --resolve --format='${ip;-16}| ${mac} | ${name;20}' --sort='-${vendor}' --localnet

Sort by Hostname (but in reverse) arp-scan --resolve --format='${ip;-16}| ${mac} | ${name;20}' -S '-${name}' --localnet


Essentially add --sort option that takes field names as input. And a -${fieldname} to reverse sort. --sort=<[-]s> or S <[-]s>

I assume that sorting would be context sensitive... so IP address, RTT. etc... would be numeric sort while Name, Hostname, Vendor, etc... would be alphanumeric sort.

royhills commented 1 year ago

The functionality seems similar to running the output through sort specifying the delimiter and key number. E.g.

arp-scan --plain --resolve --format='${ip;-16}| ${mac} | ${name;20}' --localnet | sort -t '|' -k 1

This is just sorting on text. I've added --plain to omit the header and trailer so those don't get sorted along with the data.

sort supports alphabetic and numeric sort, but not IP addresses, so arp-scan could do a better job by knowing the type of the field as you describe.

Any type of sorting will mean that nothing gets printed until all the results are returned. That could be non ideal with large address spaces.

It's an interesting idea, but may not be easy to implement. I'll give it some thought. Ideas welcome.

gspannu commented 1 year ago

arp-scan --plain --resolve --format='${ip;-16}| ${mac} | ${name;20}' --localnet | sort -t '|' -k 1 sort supports alphabetic and numeric sort, but not IP addresses, so arp-scan could do a better job by knowing the type of the field as you describe. It's an interesting idea, but may not be easy to implement. I'll give it some thought. Ideas welcome.

Thank you... It gave me some ideas.

The below 'sort command' will properly sort IP addresses... (limitation: IP address needs to be the first column).

arp-scan --plain --resolve --format='${ip;-16}| ${mac} | ${name;20}' --localnet | sort -t . -k 1,1n -k 2,2n -k 3,3n -k 4,4n

As you have written, it would be great if you could implement this !

royhills commented 1 year ago

It's easy to convert IP addresses from dotted quad format to a 32-bit integer for sorting using inet_aton in C. Here's a perl example to show what I mean:

#!/usr/bin/perl
use strict;
use warnings;

my $ipstr = "10.0.0.2";
print unpack("N", pack('C4', split(/\./, $ipstr))) . "\n";

It would be easy to add an option to output the ${ip} field as numeric, which would make sorting easier.

gspannu commented 1 year ago

It would be easy to add an option to output the ${ip} field as numeric, which would make sorting easier.

Thanks for the great work and a great utility.

Looking forward to an updated version...

royhills commented 1 year ago

PR https://github.com/royhills/arp-scan/pull/157 adds the ${IPnum} field, e.g:

rsh@bookworm:~$ arp-scan -l -F '${ipnum}\t${ip}\t${mac}\t${vendor}'
Interface: ens33, type: EN10MB, MAC: 00:0c:29:d3:97:e8, IPv4: 192.168.14.128
Target list from interface network 192.168.14.0 netmask 255.255.255.0
Starting arp-scan 1.10.1-git with 256 hosts (https://github.com/royhills/arp-scan)
3232239105      192.168.14.1    00:50:56:c0:00:08       VMware, Inc.
3232239106      192.168.14.2    00:50:56:e4:9a:83       VMware, Inc.
3232239358      192.168.14.254  00:50:56:f6:22:db       VMware, Inc.

6 packets received by filter, 0 packets dropped by kernel
Ending arp-scan 1.10.1-git: 256 hosts scanned in 2.089 seconds (122.55 hosts/sec). 3 responded
royhills commented 1 year ago

I think this could be useful for a few use cases, so I'm merging into master. e.g (using Linux):

Assign all odd addresses in 10.0.0.0/24 to device ens32 on test system:

# for I in $(seq 1 2 254); do ip address add 10.0.0.${I}/24 dev ens32; done

Scan network from another system. ~ is used as separator because it doesn't appear in the IEEE registry data. Randomise the hosts to test the sorting:

$ arp-scan -I ens35 -l --random --plain -F '${ipnum}~${ip}~${mac}~${vendor}'

Import into excel:

2023-03-10

Sort on column A:

2023-03-10 (1)

That's useful because it's not easy to sort IP addresses in excel. Not trivial to do so with sort either. So thanks for filing the issue.