Problem statement:
given a range
x -> y
of unsigned integers
wherex
andy
are both in the range
This is a kind of question I usually try to solve with a simple cumulative sum over +1/-1.
ip_address: ip is not available for ip_address, but available starting with ip_address + 1
subnet: ip is not available for ipv4_end, but available stating with ipv4_begin + 1
dhcp_range: ip is not available after begin_address, but available starting with end_address + 1
Now sum all the +1/-1 ordered by ip addresses, whenever it's greater than zero it's the start of a range of free tips and now the next row's ip is the start of a used range.
SELECT
subnet_sk
,ip_begin
,ip_end
FROM
(
SELECT
subnet_sk
,ip AS ip_begin
-- ,x
,LEAD(ip)
OVER (ORDER BY ip, x) - 1 AS ip_end
,SUM(x)
OVER (ORDER BY ip, x
ROWS UNBOUNDED PRECEDING) AS avail
FROM
(
SELECT
subnet_sk, CAST(ipv4_begin AS BIGINT)+1 AS ip, 1 AS x
FROM subnet
-- WHERE subnet_sk = 1
UNION ALL
SELECT
subnet_sk, CAST(ipv4_end AS BIGINT), -1
FROM subnet
-- WHERE subnet_sk = 1
UNION ALL
SELECT
subnet_sk, CAST(begin_address AS BIGINT), -1
FROM dhcp_range
-- WHERE subnet_sk = 1
UNION ALL
SELECT
subnet_sk, CAST(end_address AS BIGINT)+1, 1
FROM dhcp_range
-- WHERE subnet_sk = 1
UNION ALL
SELECT
subnet_sk, CAST(address AS BIGINT), -1
FROM ip_address
-- WHERE subnet_sk = 1
UNION ALL
SELECT
subnet_sk, CAST(address AS BIGINT)+1, 1
FROM ip_address
-- WHERE subnet_sk = 1
) AS dt
) AS dt
WHERE avail > 0
This will return all available ranges, for a single subnet simply uncomment the WHERE-condition: fiddle