…以下列格式描述填充规则:
Range matches can be expressed as a collection of bitwise matches. For
example,suppose that the goal is to match TCP source ports 1000 to
1999,inclusive. The binary representations of 1000 and 1999 are:
01111101000 11111001111
The following series of bitwise matches will match 1000 and 1999 and
all the values in between:
01111101xxx 0111111xxxx 10xxxxxxxxx 110xxxxxxxx 1110xxxxxxx 11110xxxxxx 1111100xxxx
which can be written as the following matches:
tcp,tp_src=0x03e8/0xfff8 tcp,tp_src=0x03f0/0xfff0 tcp,tp_src=0x0400/0xfe00 tcp,tp_src=0x0600/0xff00 tcp,tp_src=0x0700/0xff80 tcp,tp_src=0x0780/0xffc0 tcp,tp_src=0x07c0/0xfff0
我正在尝试根据perl中的最小和最大整数值来确定生成这些匹配的正确方法.我查看了模块Bit :: Vector,但我无法弄清楚如何有效地将它用于此目的.
解决方法@H_403_38@
让我们假设我们试图解决十进制的等效问题一秒钟.
假设你想要567(含)到1203(独家).
>扩大阶段
>你增加1直到你得到10的倍数,否则你会超出范围.
>⇒598(创建597-597)
>⇒599(创建598-598)
>⇒600(创建599-599)
>你增加10,直到你有100的倍数或你会超出范围.
>增加100,直到你有1000的倍数,否则你会超出范围.
>⇒700(创建600-699)
>⇒800(创建700-799)
>⇒900(创建800-899)
>⇒1000(创建900-999)
>您增加1000,直到您有10000的倍数或超出范围.
> [超出限制]
>收缩阶段
>您将增加100,直到超出范围.
>⇒1100(创建1000-1099)
>⇒1200(创建1100-1199)
>⇒1201(创建1200-1200)
>⇒1202(创建1201-1201)
>⇒1203(创建1202-1202)
二进制相同,但功率为2而不是10的幂.
my $start = 1000;
my $end = 1999 + 1;
my @ranges;
my $this = $start;
my $this_power = 1;
OUTER: while (1) {
my $next_power = $this_power * 2;
while ($this % $next_power) {
my $next = $this + $this_power;
last OUTER if $next > $end;
my $mask = ~($this_power - 1) & 0xFFFF;
push @ranges,sprintf("0x%04x/0x%x",$this,$mask);
$this = $next;
}
$this_power = $next_power;
}
while ($this_power > 1) {
$this_power /= 2;
while (1) {
my $next = $this + $this_power;
last if $next > $end;
my $mask = ~($this_power - 1) & 0xFFFF;
push @ranges,$mask);
$this = $next;
}
}
say for @ranges;
我们可以通过利用我们处理二进制的事实来优化它.
my $start = 1000;
my $end = 1999 + 1;
my @ranges;
my $this = $start;
my $power = 1;
my $mask = 0xFFFF;
while ($start & $mask) {
if ($this & $power) {
push @ranges,$mask);
$this += $power;
}
$mask &= ~$power;
$power <<= 1;
}
while ($end & ~$mask) {
$power >>= 1;
$mask |= $power;
if ($end & $power) {
push @ranges,$mask);
$this |= $power;
}
}
say for @ranges;
输出:
0x03e8/0xfff8
0x03f0/0xfff0
0x0400/0xfe00
0x0600/0xff00
0x0700/0xff80
0x0780/0xffc0
0x07c0/0xfff0
假设你想要567(含)到1203(独家).
>扩大阶段
>你增加1直到你得到10的倍数,否则你会超出范围.
>⇒598(创建597-597)
>⇒599(创建598-598)
>⇒600(创建599-599)
>你增加10,直到你有100的倍数或你会超出范围.
>增加100,直到你有1000的倍数,否则你会超出范围.
>⇒700(创建600-699)
>⇒800(创建700-799)
>⇒900(创建800-899)
>⇒1000(创建900-999)
>您增加1000,直到您有10000的倍数或超出范围.
> [超出限制]
>收缩阶段
>您将增加100,直到超出范围.
>⇒1100(创建1000-1099)
>⇒1200(创建1100-1199)
>⇒1201(创建1200-1200)
>⇒1202(创建1201-1201)
>⇒1203(创建1202-1202)
二进制相同,但功率为2而不是10的幂.
my $start = 1000; my $end = 1999 + 1; my @ranges; my $this = $start; my $this_power = 1; OUTER: while (1) { my $next_power = $this_power * 2; while ($this % $next_power) { my $next = $this + $this_power; last OUTER if $next > $end; my $mask = ~($this_power - 1) & 0xFFFF; push @ranges,sprintf("0x%04x/0x%x",$this,$mask); $this = $next; } $this_power = $next_power; } while ($this_power > 1) { $this_power /= 2; while (1) { my $next = $this + $this_power; last if $next > $end; my $mask = ~($this_power - 1) & 0xFFFF; push @ranges,$mask); $this = $next; } } say for @ranges;
我们可以通过利用我们处理二进制的事实来优化它.
my $start = 1000; my $end = 1999 + 1; my @ranges; my $this = $start; my $power = 1; my $mask = 0xFFFF; while ($start & $mask) { if ($this & $power) { push @ranges,$mask); $this += $power; } $mask &= ~$power; $power <<= 1; } while ($end & ~$mask) { $power >>= 1; $mask |= $power; if ($end & $power) { push @ranges,$mask); $this |= $power; } } say for @ranges;
输出:
0x03e8/0xfff8 0x03f0/0xfff0 0x0400/0xfe00 0x0600/0xff00 0x0700/0xff80 0x0780/0xffc0 0x07c0/0xfff0