在Perl中为二进制字符串添加一个最简单的方法是什么?

时间:2022-04-11 11:49:40

I have a variable that contains a 4 byte, network-order IPv4 address (this was created using pack and the integer representation). I have another variable, also a 4 byte network-order, subnet. I'm trying to add them together and add one to get the first IP in the subnet.

我有一个包含4字节网络顺序IPv4地址的变量(这是使用pack和整数表示创建的)。我有另一个变量,也是一个4字节的网络顺序子网。我正在尝试将它们添加到一起并添加一个以获取子网中的第一个IP。

To get the ASCII representation, I can do inet_ntoa($ip&$netmask) to get the base address, but it's an error to do inet_ntoa((($ip&$netmask)+1); I get a message like:

要获得ASCII表示,我可以使用inet_ntoa($ ip&$ netmask)来获取基址,但是执行inet_ntoa(($ ip&$ netmask)+1)是错误的;我收到如下消息:

 Argument "\n\r&\0" isn't numeric in addition (+) at test.pm line 95.

So what's happening, the best as I can tell, is it's looking at the 4 bytes, and seeing that the 4 bytes don't represent a numeric string, and then refusing to add 1.

所以正在发生的事情,我能说的最好的是,它正在查看4个字节,并看到4个字节不代表数字字符串,然后拒绝添加1。

Another way of putting it: What I want it to do is add 1 to the least significant byte, which I know is the 4th byte? That is, I want to take the string \n\r&\0 and end up with the string \n\r&\1. What's the simplest way of doing that?

放置它的另一种方法:我想要它做的是将最低有效字节加1,我知道是第4个字节?也就是说,我想取字符串\ n \ r&\ 0并以字符串\ n \ r&1结束。这样做最简单的方法是什么?

Is there a way to do this without having to unpack and re-pack the variable?

有没有办法做到这一点,而无需解压缩和重新包装变量?

2 个解决方案

#1


13  

What's happening is that you make a byte string with $ip&$netmask, and then try to treat it as a number. This is not going to work, as such. What you have to feed to inet_ntoa is.

发生的事情是你使用$ ip和$ netmask创建一个字节字符串,然后尝试将其视为一个数字。这不会起作用。你必须提供给inet_ntoa的是什么。

pack("N", unpack("N", $ip&$netmask) + 1)

I don't think there is a simpler way to do it.

我认为没有更简单的方法可以做到这一点。

#2


8  

Confusing integers and strings. Perhaps the following code will help:

令人困惑的整数和字符串。也许以下代码将有所帮助:

use Socket;

$ip = pack("C4", 192,168,250,66); # why not inet_aton("192.168.250.66")
$netmask = pack("C4", 255,255,255,0);

$ipi = unpack("N", $ip);
$netmaski = unpack("N", $netmask);

$ip1 = pack("N", ($ipi&$netmaski)+1);
print inet_ntoa($ip1), "\n";

Which outputs:

192.168.250.1

#1


13  

What's happening is that you make a byte string with $ip&$netmask, and then try to treat it as a number. This is not going to work, as such. What you have to feed to inet_ntoa is.

发生的事情是你使用$ ip和$ netmask创建一个字节字符串,然后尝试将其视为一个数字。这不会起作用。你必须提供给inet_ntoa的是什么。

pack("N", unpack("N", $ip&$netmask) + 1)

I don't think there is a simpler way to do it.

我认为没有更简单的方法可以做到这一点。

#2


8  

Confusing integers and strings. Perhaps the following code will help:

令人困惑的整数和字符串。也许以下代码将有所帮助:

use Socket;

$ip = pack("C4", 192,168,250,66); # why not inet_aton("192.168.250.66")
$netmask = pack("C4", 255,255,255,0);

$ipi = unpack("N", $ip);
$netmaski = unpack("N", $netmask);

$ip1 = pack("N", ($ipi&$netmaski)+1);
print inet_ntoa($ip1), "\n";

Which outputs:

192.168.250.1