【问题标题】:PostgreSQL: How to split IPv6 network address into two halvesPostgreSQL:如何将 IPv6 网络地址分成两半
【发布时间】:2014-07-07 12:26:46
【问题描述】:

在 PostgreSQL 中,我需要找到一种方法将 IPv6 子网分成两半,即。计算共同构成输入子网的两个 IPv6 地址,如下所示:

"1::/64" should give "1::/65" and "1:0:0:0:8000::/65"

知道怎么做吗?我有这个用于 IPv4 的函数,但它使用的算法不适用于 128 位数字(net_ip 是要拆分的子网地址):

SELECT * INTO STRICT net_old FROM subnet WHERE subnet_i = _subnet_i;
mask := masklen(net_old.net_ip);
nsize := 2^(31 - mask);
_addr_new_1 := set_masklen(net_old.net_ip, mask + 1);
_addr_new_2 := set_masklen(net_old.net_ip, mask + 1) + nsize;

【问题讨论】:

  • 也许你应该展示这些算术?第一个很容易,但我不明白另一个是从哪里来的。
  • 我添加了适用于 IPv4 地址的代码。

标签: postgresql networking split ipv6 inet


【解决方案1】:

我想我找到了一个解决方案,在 PgPL/SQL 中完成了功能,它适用于 IPv4 和 IPv6:

CREATE OR REPLACE FUNCTION cidr_split_subnet(
  _subnet cidr,
  OUT _addr_low cidr,
  OUT _addr_hi cidr
) AS $$

BEGIN

_addr_low := set_masklen(_subnet, masklen(_subnet) + 1);
_addr_hi  := set_masklen(_subnet | ~netmask(_addr_low) - 1 , masklen(_addr_low));

END;

$$ LANGUAGE 'plpgsql';

例子:

=> SELECT cidr_split_subnet('1::/64');
     cidr_split_subnet     
---------------------------
 (1::/65,1::8000:0:0:0/65)

=> SELECT cidr_split_subnet('192.168/16');
         cidr_split_subnet         
-----------------------------------
 (192.168.0.0/17,192.168.128.0/17)

【讨论】:

    猜你喜欢
    • 2020-11-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-02-11
    • 2013-02-22
    • 2011-02-16
    相关资源
    最近更新 更多