如何使用 awk 将 mac addr 转换为 int?

How to convert mac addr to int using awk?

输入:

192.168.0.1 aa:bb:cc:00:11:22 192.168.0.1 aa:00:bb:11:cc:22
192.168.10.11 2a:bb:cc:20:11:22 192.168.10.11 aa:02:bb:21:cc:22

输出:

3232235521 187723558162722 3232235521 186920115227682
3232238091 46986071904546 3232238091 186928706210850

我知道如何在 python3 中将 mac 转换为整数(十六进制 -> 整数) : mac = int(mac.replace(':', ''), 16) 但我无法在 shell 中应用此方法。也不知道IP to Int.

我想像这样使用 awk:

awk '{,=??, ,=???}' tmpfile > newfile

对于 strtonum() 使用 GNU awk:

$ echo 'aa:bb:cc:00:11:22' | awk '{gsub(/:/,""); print strtonum("0x"[=10=])}'
187723558162722

$ echo '192.168.0.1' | awk '{split([=10=],o,/[.]/); print o[1]*256^3 + o[2]*256^2 + o[3]*256 + o[4]}'
3232235521

$ cat tst.awk
function ip2int(ip,  o) { split(ip,o,/[.]/); return o[1]*256^3 + o[2]*256^2 + o[3]*256 + o[4] }
function mac2int(mac)   { gsub(/:/,"",mac); return strtonum("0x"mac) }
{ print ip2int(), mac2int(), ip2int(), mac2int() }

$ awk -f tst.awk file
3232235521 187723558162722 3232235521 186920115227682
3232238091 46986071904546 3232238091 186928706210850

试试这个 Perl 单行代码

$ cat matii.txt
192.168.0.1 aa:bb:cc:00:11:22 192.168.0.1 aa:00:bb:11:cc:22
192.168.10.11 2a:bb:cc:20:11:22 192.168.10.11 aa:02:bb:21:cc:22

perl -pe ' s/(\d+)\.(\d+)\.(\d+).(\d+)/*256**3+*256**2+*256+/ge; s/://g ; s/\S+\s+\K(\S+)/hex()/ge;' matii.txt
3232235521 187723558162722 3232235521 186920115227682
3232238091 46986071904546 3232238091 186928706210850

Perl 相当于

mac = int(mac.replace(':', ''), 16)

$mac = hex( $max =~ s/://rg )

解决方案:

perl -nle'print join " ", unpack "N Q> N Q>", pack "( C4 xx(H2)6 )2", /[0-9a-fA-F]+/g'


更清晰的解决方案:

perl -lane'
   sub ipv4_to_dec { unpack "N", pack "C4", split /\./, $_[0] }
   sub mac_to_dec { hex( $_[0] =~ s/://rg ) }
   print join " ",
      ipv4_to_dec($F[0]), mac_to_dec($F[1]),
      ipv4_to_dec($F[2]), mac_to_dec($F[3]);
'

perl -ple'
   sub ipv4_to_dec { unpack "N", pack "C4", split /\./, $_[0] }
   sub mac_to_dec { hex( $_[0] =~ s/://rg ) }
   s{\G(\s*)(\S+)(\s+)(\S+)}{  . ipv4_to_dec() .  . mac_to_dec() }eg;
'