Anonymous user
Module:IP: Difference between revisions
From the Croc Wiki, the Croc encyclopedia
Jump to navigationJump to search
some more style changes (it's still broken but I'll fix it later; also, sorry for the edit conflict)
(Collection is good (I've always meant to fix it) but in case you don't have other plans, here is a change to make it work) |
(some more style changes (it's still broken but I'll fix it later; also, sorry for the edit conflict)) |
||
Line 10:
local V4 = 'IPv4'
local V6 = 'IPv6'
--------------------------------------------------------------------------------
Line 45 ⟶ 22:
RawIP.__index = RawIP
do
-- Collection class.
-- This is a table used to hold items.
local Collection
do
local mt = {
__index = {
self.n = self.n + 1
self[self.n] = item
end,
join = function (self, sep)
return table.concat(self, sep)
end,
}
}
Collection = function ()
return setmetatable({n = 0}, mt)
end
end
-- Constructors
function RawIP.newFromIPv4(ipStr)
-- If ipStr is a valid IPv4 string, return a collection of its parts.
-- Otherwise, return nil.
-- This representation is for compatibility with IPv6 addresses.
local octets = Collection()
local s = ipStr:match('^%s*(.-)%s*$') .. '.'
for item in s:gmatch('(.-)%.') do
octets:add(item)
end
if octets.n == 4 then
for i, s in ipairs(octets) do
if s:match('^%d+$') then
local num = tonumber(s)
if 0 <= num and num <= 255 then
if num > 0 and s:match('^0') then
-- A redundant leading zero is for an IP in octal.
return false
end
octets[i] = num
else
return false
end
else
return false
end
end
local parts = Collection()
for i = 1, 3, 2 do
parts:add(octets[i] * 256 + octets[i+1])
end
return setmetatable(parts, RawIP)
end
return nil
end
function RawIP.newFromIPv6(ipStr)
-- If ipStr is a valid IPv6 string, return a collection of its parts.
-- Otherwise, return nil.
ipStr = ipStr:match('^%s*(.-)%s*$')
local _, n = ipStr:gsub(':', ':')
if n < 7 then
ipStr, n = ipStr:gsub('::', string.rep(':', 9 - n))
end
local parts = Collection()
for
parts:add(
end
for i, s in ipairs(parts) do
if s == '' then
parts[i] = 0
else
local num = tonumber('0x' .. s)
if num and 0 <= num and num <= 65535 then
parts[i] = num
else
return false
end
end
end
return setmetatable(parts, RawIP)
end
return
end
function RawIP:getAdjacent(previous)
-- Return a RawIP object for an adjacent IP address. If previous is true
-- then the previous IP is returned; otherwise the next IP is returned.
-- Will wraparound:
-- next 255.255.255.255 → 0.0.0.0
-- ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff → ::
-- previous 0.0.0.0 → 255.255.255.255
-- :: → ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff
local result = Collection()
local carry = down and 0xffff or 1
for i = self.n, 1, -1 do
else
carry = down and 0xffff or 0
end
result[i] = sum
end
return setmetatable(result, RawIP)
end
-- Methods
function RawIP:getPrefix(length)
-- Return a copy of IPv4 or IPv6 parts, masked to length.
if length >
length = length - 16
else
result[i] = bit32.band(self[i],
bit32.arshift(0xffff8000, length - 1))
length = 0
end
else
result[i] =
end
end
return setmetatable(result, RawIP)
end
function RawIP:setHostBits(length)
width = bits
width = 0
width = bits - length
if width > 0 then
if width >= 16 then
result[i] = 0xffff
width = width - 16
else
result[i] = bit32.replace(self[i], 0xffff, width - 1, width)
width = 0
end
else
result[i] =
end
end
return setmetatable(result, rawIP)
end
function RawIP:_makeIPv6String()
-- Find left-most occurrence of longest run of two or more zeros.
if i < 9 and self[i] == 0 then
if zstart then
zcount = zcount + 1
else
zstart = i
zcount = 1
end
else
if zcount and zcount > 1 then
if not z1 or zcount
z1 = zstart
z2 = zstart + zcount - 1
end
end
zstart = nil
zcount = nil
end
end
local parts = Collection()
for i = 1, 8 do
if z1 and z1 <= i and i <= z2 then
if
if
if z1 == 1
return '::'
parts:add(':')
else
parts:add('')
end
end
else
parts:add(string.format('%x', self[i]))
end
end
return parts:join(':')
end
function RawIP:_makeIPv4String()
-- Return an IPv4 string representation of the object. Behavior is undefined
-- if the current object is IPv6.
local parts = Collection()
for i = 1, 2 do
local w = self[i]
parts:add(math.floor(w / 256))
parts:add(w % 256)
end
return parts:join('.')
end
function RawIP:__tostring()
-- Return a string equivalent to given IP address (IPv4 or IPv6).
if self.n == 2 then
return self:_makeIPv4String()
else
return self:_makeIPv6String()
end
end
function RawIP:
if self.n == obj.n then
for i = 1, self.n do
if self[i] ~= obj[i] then
return self[i] < obj[i]
end
end
return false
end
return self.n < obj.n
end
function RawIP:
if self.n == obj.n then
for i = 1, self.n do
return false
end
end
return true
end
return false
end
end
Line 258 ⟶ 284:
local IPAddress = {}
local newIPFromRaw
--
-- to be accessible from the Subnet class but it should not be public.
do
Line 267 ⟶ 293:
-- Metamethods that don't need upvalues
local function ipEquals(ip1, ip2)
end
local function ipLessThan(ip1, ip2)
end
local function concatIPs(ip1, ip2)
return
end
local function ipToString(ip)
return
end
-- Constructors
-- Constructs a new IPAddress object from
-- is for internal use; it is called by IPAddress.new and
--
-- should not be available to other modules.
assert(type(rawIP) == 'table', 'rawIP was type ' .. type(rawIP) .. '; expected type table')
-- Set up structure
local obj = {}
local data = {
version =
}
-- Public methods
function obj:getIP()
return
end
Line 326 ⟶ 333:
function obj:getHighestIP(bitLength)
return
end
function obj:getPrefix(bitLength)
return
end
Line 352 ⟶ 359:
function obj:getNextIP()
return
end
function obj:getPreviousIP()
return
end
Line 375 ⟶ 382:
function IPAddress.new(ip)
checkType('IPAddress.new', 1, ip, 'string')
local
if not
error('invalid IP', 2)
end
return
end
end
|