xips
"xips" (for eXpand IPS) is a console program that parses stdin for ip addresses and "summarized" ip addresses and outputs them individually, suitable for use with xargs. For instance:
echo 172.20.141.0/24 | xips | xargs -n 1 tcping -n 1
Alternatively, with the "-s" or "--summarize" flag, xips will take the same input and attempt to summarize those ip addressess into IP ranges, suitable for use in (for instance) Cisco ASA configuration files. By default it will make (ipv4) subnets no smaller than /24, but that is adjustable via -m.
I am using the same ip address range syntax as in ips. (which is an IP address range aware grep-like tool)
Usage:
Syntax: your_command | xips [-4] [-6] [-v] [--cidr|--mask] [file ...] Eats STDIN, expands IP addresses. Options: -4 : expand IPv4 addresses only -6 : expand IPv6 addresses only -s : summarize, rather than expand (collapses at > 50% utilization by default) --sort : expand, dedupe and sort numerically -m X : summarize to a max depth of /X (also --max-depth X) --mask : output subnet mask notation instead of cidr --asa : output asa network-object notation -f file: read input from file instead of stdin (also --file; may be repeated) -v : Display version information --threshold X : set summarize collapse threshold percentage, 1-100 (default: 50) --max-depth-ipv4 X : summarize to a max cidr of X for IPv4 only --max-depth-ipv6 X : summarize to a max cidr of X for IPv6 only --count : count unique IPs and print total instead of outputting them --shuffle : output IPs in random order (deduplicates like --sort) --port N : append port suffix to each IP (1.2.3.4:N or [::1]:N) --private : only output private/RFC1918 addresses --public : only output non-private addresses --hosts : exclude network and broadcast (first/last) addresses from ranges --mac-to-ipv6 : convert MAC addresses to EUI-64 link-local IPv6 (fe80::) --ipv6-to-mac : extract MAC from EUI-64 MAC-derived IPv6 addresses --anyway : bypass the >1000000 address guard rail --exclude R : exclude range R from output (may be repeated) --cidr-list : decompose range into exact covering CIDR blocks --hex-be : output IPs as big-endian hex (also --hex) --hex-le : output IPs as little-endian hex --to-mapped : output IPv4 addresses as ::ffff:x.x.x.x (IPv4-mapped IPv6) --arpa : output IPs as reverse-DNS zone names (in-addr.arpa / ip6.arpa) --subnet-info : for each input subnet, print TSV row: Network/Broadcast/Mask/Wildcard/Prefix/FirstHost/LastHost/Total/Usable --check IP : check if IP or subnet is within/overlaps input ranges (may repeat; also --check-file FILE) --diff FILE : output CIDRs from input ranges NOT covered by ranges in FILE Hex input accepted: 0xAABBCCDD \xAA\xBB... %AA%BB... 0b<32bits> AABBCCDD IP/Range Syntax: 192.168.1.1 192.168.1.1-192.168.1.255 192.168.1.1/24 192.168.1.1/C '192.168.1.1 255.255.255.0' 192.168.1.5-15
Action shots:
$echo 192.168.100.5-10 | xips
192.168.100.5
192.168.100.6
192.168.100.7
192.168.100.8
192.168.100.9
192.168.100.10
$cat example.txt
192.168.0.1
192.168.0.2
192.168.0.3
10.0.10.0
10.0.10.1
10.0.10.2
10.0.10.3
10.0.10.4
10.0.10.5
10.0.10.200
172.20.5.6
172.20.5.6
$cat example.txt | xips -s
10.0.10.0 255.255.255.0
172.20.5.0 255.255.255.0
192.168.0.0 255.255.255.0
$cat example.txt | xips -s -m 30
10.0.10.0 255.255.255.248
10.0.10.200 255.255.255.252
172.20.5.4 255.255.255.252
192.168.0.0 255.255.255.252
$echo "192.168.20.1-5" | xips | xargs -n 1 tcping -n 1
Probing 192.168.20.1:80/tcp - Port is open - time=0.782ms
Ping statistics for 192.168.20.1:80
1 probes sent.
1 successful, 0 failed.
Approximate trip times in milli-seconds:
Minimum = 0.782ms, Maximum = 0.782ms, Average = 0.782ms
Probing 192.168.20.2:80/tcp - Port is open - time=0.813ms
Ping statistics for 192.168.20.2:80
1 probes sent.
1 successful, 0 failed.
Approximate trip times in milli-seconds:
Minimum = 0.813ms, Maximum = 0.813ms, Average = 0.813ms
Probing 192.168.20.3:80/tcp - No response - time=2001.949ms
Ping statistics for 192.168.20.3:80
1 probes sent.
0 successful, 1 failed.
Was unable to connect, cannot provide trip statistics.
Probing 192.168.20.4:80/tcp - No response - time=2001.538ms
Ping statistics for 192.168.20.4:80
1 probes sent.
0 successful, 1 failed.
Was unable to connect, cannot provide trip statistics.
Probing 192.168.20.5:80/tcp - Port is open - time=1.107ms
Ping statistics for 192.168.20.5:80
1 probes sent.
1 successful, 0 failed.
Approximate trip times in milli-seconds:
Minimum = 1.107ms, Maximum = 1.107ms, Average = 1.107ms
Downloads:
Listing directory https://download.elifulkerson.com/files/xips/0.6:LICENSE June 01 2026 03:27:59 35149 ASCII text
Makefile June 01 2026 02:51:07 2173 makefile script, ASCII text, with very long lines
README.md June 01 2026 00:35:24 5718 UTF-8 Unicode text
dist June 01 2026 03:43:31 - directory
maketests.py May 12 2026 06:53:32 37652 Python script, UTF-8 Unicode text executable
xips.1 June 01 2026 00:36:49 5935 troff or preprocessor input, ASCII text
xips.cpp May 31 2026 19:06:18 95841 C++ source, ASCII text, with very long lines, with CRLF line terminators
xips.cpp.asc June 01 2026 03:35:57 801 GnuPG signature
xips.cpp.md5 June 01 2026 03:35:57 43 MD5 checksum
xips.cpp.sha1 June 01 2026 03:35:57 51 SHA1 checksum
xips.cpp.sha256 June 01 2026 03:35:57 75 SHA256 checksum
xips.cpp.sha512 June 01 2026 03:35:57 139 SHA512 checksum ↩ Browse the download server
To compile: g++ -std=c++11 -o xips xips.cpp
Updates:
Update: Jan 5 2018, v0.1. Initial release.
Update: Jan 6 2018, v0.2. Fix so it compiles properly with -std=c++11. Added .exe version for windows folks (you will need the cygwin dlls).
Update: Apr 5 2018, v0.3. Oops - some of the formats were broken because I made some bad assumptions. /C, /24 and more variations of "-", "to", etc will work correctly now. Also "thru", because of John.
Update: Apr 30 2018, v0.5. Added "--asa" - which outputs the format "network-object host blah" etc. Also changed summary to have default max depth of /32.
Update: June 1 2026, v0.6. Multiple feature update.
License:
GPLv3
See Also:
ips - an ip address aware "grep" analog which xips' parsing logic is based on