mirror of
https://github.com/retspen/webvirtcloud
synced 2024-12-24 23:25:24 +00:00
commit
9977c650db
20 changed files with 15412 additions and 15050 deletions
|
@ -1,4 +1,4 @@
|
|||
FROM phusion/baseimage:focal-1.0.0
|
||||
FROM phusion/baseimage:focal-1.1.0
|
||||
|
||||
EXPOSE 80
|
||||
EXPOSE 6080
|
||||
|
|
|
@ -32,7 +32,7 @@ WebVirtCloud is a virtualization web interface for admins and users. It can dele
|
|||
|
||||
## Quick Install with Installer (Beta)
|
||||
|
||||
Install an OS and run specified commands. Installer supported OSes: Ubuntu 18.04, Debian 10, Centos/OEL/RHEL 8.
|
||||
Install an OS and run specified commands. Installer supported OSes: Ubuntu 18.04/20.04, Debian 10/11, Centos/OEL/RHEL 8.
|
||||
It can be installed on a virtual machine, physical host or on a KVM host.
|
||||
|
||||
```bash
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
Django==3.2.10
|
||||
Django==3.2.11
|
||||
django_bootstrap5==21.2
|
||||
django-icons==21.1
|
||||
django-login-required-middleware==0.7
|
||||
|
|
|
@ -4,4 +4,4 @@ django-debug-toolbar==3.2.4
|
|||
pycodestyle==2.8.0
|
||||
pyflakes==2.4.0
|
||||
pylint==2.12.2
|
||||
yapf==0.31.0
|
||||
yapf==0.32.0
|
||||
|
|
|
@ -342,15 +342,17 @@ def migrate(request, pk):
|
|||
compress = request.POST.get("compress", False)
|
||||
postcopy = request.POST.get("postcopy", False)
|
||||
|
||||
new_compute = Compute.objects.get(id=compute_id)
|
||||
current_host = instance.compute.hostname
|
||||
target_host = Compute.objects.get(id=compute_id)
|
||||
|
||||
try:
|
||||
utils.migrate_instance(new_compute, instance, request.user, live, unsafe, xml_del, offline)
|
||||
utils.migrate_instance(target_host, instance, request.user, live, unsafe, xml_del, offline)
|
||||
except libvirtError as err:
|
||||
messages.error(request, err)
|
||||
|
||||
msg = _("Instance is migrated to %(hostname)s") % {"hostname": new_compute.hostname}
|
||||
addlogmsg(request.user.username, instance.compute.hostname, instance.name, msg)
|
||||
migration_method = "live" if live is True else "offline"
|
||||
msg = _("Instance is migrated(%(method)s) to %(hostname)s") % {"hostname": target_host.hostname, "method": migration_method}
|
||||
addlogmsg(request.user.username, current_host, instance.name, msg)
|
||||
|
||||
return redirect(request.META.get("HTTP_REFERER"))
|
||||
|
||||
|
|
Binary file not shown.
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
Binary file not shown.
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
Binary file not shown.
File diff suppressed because it is too large
Load diff
|
@ -6,128 +6,131 @@ Further Information might be available at:
|
|||
https://github.com/haypo/python-ipy
|
||||
"""
|
||||
|
||||
__version__ = "1.00"
|
||||
__version__ = '1.01'
|
||||
|
||||
import bisect
|
||||
import collections
|
||||
import sys
|
||||
import types
|
||||
try:
|
||||
import collections.abc as collections_abc
|
||||
except ImportError:
|
||||
import collections as collections_abc
|
||||
|
||||
# Definition of the Ranges for IPv4 IPs
|
||||
# this should include www.iana.org/assignments/ipv4-address-space
|
||||
# and www.iana.org/assignments/multicast-addresses
|
||||
IPv4ranges = {
|
||||
"0": "PUBLIC", # fall back
|
||||
"00000000": "PRIVATE", # 0/8
|
||||
"00001010": "PRIVATE", # 10/8
|
||||
"0110010001": "CARRIER_GRADE_NAT", # 100.64/10
|
||||
"01111111": "LOOPBACK", # 127.0/8
|
||||
"1": "PUBLIC", # fall back
|
||||
"1010100111111110": "PRIVATE", # 169.254/16
|
||||
"101011000001": "PRIVATE", # 172.16/12
|
||||
"1100000010101000": "PRIVATE", # 192.168/16
|
||||
"111": "RESERVED", # 224/3
|
||||
}
|
||||
'0': 'PUBLIC', # fall back
|
||||
'00000000': 'PRIVATE', # 0/8
|
||||
'00001010': 'PRIVATE', # 10/8
|
||||
'0110010001': 'CARRIER_GRADE_NAT', #100.64/10
|
||||
'01111111': 'LOOPBACK', # 127.0/8
|
||||
'1': 'PUBLIC', # fall back
|
||||
'1010100111111110': 'PRIVATE', # 169.254/16
|
||||
'101011000001': 'PRIVATE', # 172.16/12
|
||||
'1100000010101000': 'PRIVATE', # 192.168/16
|
||||
'111': 'RESERVED', # 224/3
|
||||
}
|
||||
|
||||
# Definition of the Ranges for IPv6 IPs
|
||||
# http://www.iana.org/assignments/ipv6-address-space/
|
||||
# http://www.iana.org/assignments/ipv6-unicast-address-assignments/
|
||||
# http://www.iana.org/assignments/ipv6-multicast-addresses/
|
||||
IPv6ranges = {
|
||||
"00000000": "RESERVED", # ::/8
|
||||
"0" * 96: "RESERVED", # ::/96 Formerly IPV4COMP [RFC4291]
|
||||
"0" * 128: "UNSPECIFIED", # ::/128
|
||||
"0" * 127 + "1": "LOOPBACK", # ::1/128
|
||||
"0" * 80 + "1" * 16: "IPV4MAP", # ::ffff:0:0/96
|
||||
"00000000011001001111111110011011" + "0" * 64: "WKP46TRANS", # 0064:ff9b::/96 Well-Known-Prefix [RFC6052]
|
||||
"00000001": "UNASSIGNED", # 0100::/8
|
||||
"0000001": "RESERVED", # 0200::/7 Formerly NSAP [RFC4048]
|
||||
"0000010": "RESERVED", # 0400::/7 Formerly IPX [RFC3513]
|
||||
"0000011": "RESERVED", # 0600::/7
|
||||
"00001": "RESERVED", # 0800::/5
|
||||
"0001": "RESERVED", # 1000::/4
|
||||
"001": "GLOBAL-UNICAST", # 2000::/3 [RFC4291]
|
||||
"00100000000000010000000": "SPECIALPURPOSE", # 2001::/23 [RFC4773]
|
||||
"00100000000000010000000000000000": "TEREDO", # 2001::/32 [RFC4380]
|
||||
"00100000000000010000000000000010" + "0" * 16: "BMWG", # 2001:0002::/48 Benchmarking [RFC5180]
|
||||
"0010000000000001000000000001": "ORCHID", # 2001:0010::/28 (Temp until 2014-03-21) [RFC4843]
|
||||
"00100000000000010000001": "ALLOCATED APNIC", # 2001:0200::/23
|
||||
"00100000000000010000010": "ALLOCATED ARIN", # 2001:0400::/23
|
||||
"00100000000000010000011": "ALLOCATED RIPE NCC", # 2001:0600::/23
|
||||
"00100000000000010000100": "ALLOCATED RIPE NCC", # 2001:0800::/23
|
||||
"00100000000000010000101": "ALLOCATED RIPE NCC", # 2001:0a00::/23
|
||||
"00100000000000010000110": "ALLOCATED APNIC", # 2001:0c00::/23
|
||||
"00100000000000010000110110111000": "DOCUMENTATION", # 2001:0db8::/32 [RFC3849]
|
||||
"00100000000000010000111": "ALLOCATED APNIC", # 2001:0e00::/23
|
||||
"00100000000000010001001": "ALLOCATED LACNIC", # 2001:1200::/23
|
||||
"00100000000000010001010": "ALLOCATED RIPE NCC", # 2001:1400::/23
|
||||
"00100000000000010001011": "ALLOCATED RIPE NCC", # 2001:1600::/23
|
||||
"00100000000000010001100": "ALLOCATED ARIN", # 2001:1800::/23
|
||||
"00100000000000010001101": "ALLOCATED RIPE NCC", # 2001:1a00::/23
|
||||
"0010000000000001000111": "ALLOCATED RIPE NCC", # 2001:1c00::/22
|
||||
"00100000000000010010": "ALLOCATED RIPE NCC", # 2001:2000::/20
|
||||
"001000000000000100110": "ALLOCATED RIPE NCC", # 2001:3000::/21
|
||||
"0010000000000001001110": "ALLOCATED RIPE NCC", # 2001:3800::/22
|
||||
"0010000000000001001111": "RESERVED", # 2001:3c00::/22 Possible future allocation to RIPE NCC
|
||||
"00100000000000010100000": "ALLOCATED RIPE NCC", # 2001:4000::/23
|
||||
"00100000000000010100001": "ALLOCATED AFRINIC", # 2001:4200::/23
|
||||
"00100000000000010100010": "ALLOCATED APNIC", # 2001:4400::/23
|
||||
"00100000000000010100011": "ALLOCATED RIPE NCC", # 2001:4600::/23
|
||||
"00100000000000010100100": "ALLOCATED ARIN", # 2001:4800::/23
|
||||
"00100000000000010100101": "ALLOCATED RIPE NCC", # 2001:4a00::/23
|
||||
"00100000000000010100110": "ALLOCATED RIPE NCC", # 2001:4c00::/23
|
||||
"00100000000000010101": "ALLOCATED RIPE NCC", # 2001:5000::/20
|
||||
"0010000000000001100": "ALLOCATED APNIC", # 2001:8000::/19
|
||||
"00100000000000011010": "ALLOCATED APNIC", # 2001:a000::/20
|
||||
"00100000000000011011": "ALLOCATED APNIC", # 2001:b000::/20
|
||||
"0010000000000010": "6TO4", # 2002::/16 "6to4" [RFC3056]
|
||||
"001000000000001100": "ALLOCATED RIPE NCC", # 2003::/18
|
||||
"001001000000": "ALLOCATED APNIC", # 2400::/12
|
||||
"001001100000": "ALLOCATED ARIN", # 2600::/12
|
||||
"00100110000100000000000": "ALLOCATED ARIN", # 2610::/23
|
||||
"00100110001000000000000": "ALLOCATED ARIN", # 2620::/23
|
||||
"001010000000": "ALLOCATED LACNIC", # 2800::/12
|
||||
"001010100000": "ALLOCATED RIPE NCC", # 2a00::/12
|
||||
"001011000000": "ALLOCATED AFRINIC", # 2c00::/12
|
||||
"00101101": "RESERVED", # 2d00::/8
|
||||
"0010111": "RESERVED", # 2e00::/7
|
||||
"0011": "RESERVED", # 3000::/4
|
||||
"010": "RESERVED", # 4000::/3
|
||||
"011": "RESERVED", # 6000::/3
|
||||
"100": "RESERVED", # 8000::/3
|
||||
"101": "RESERVED", # a000::/3
|
||||
"110": "RESERVED", # c000::/3
|
||||
"1110": "RESERVED", # e000::/4
|
||||
"11110": "RESERVED", # f000::/5
|
||||
"111110": "RESERVED", # f800::/6
|
||||
"1111110": "ULA", # fc00::/7 [RFC4193]
|
||||
"111111100": "RESERVED", # fe00::/9
|
||||
"1111111010": "LINKLOCAL", # fe80::/10
|
||||
"1111111011": "RESERVED", # fec0::/10 Formerly SITELOCAL [RFC4291]
|
||||
"11111111": "MULTICAST", # ff00::/8
|
||||
"1111111100000001": "NODE-LOCAL MULTICAST", # ff01::/16
|
||||
"1111111100000010": "LINK-LOCAL MULTICAST", # ff02::/16
|
||||
"1111111100000100": "ADMIN-LOCAL MULTICAST", # ff04::/16
|
||||
"1111111100000101": "SITE-LOCAL MULTICAST", # ff05::/16
|
||||
"1111111100001000": "ORG-LOCAL MULTICAST", # ff08::/16
|
||||
"1111111100001110": "GLOBAL MULTICAST", # ff0e::/16
|
||||
"1111111100001111": "RESERVED MULTICAST", # ff0f::/16
|
||||
"111111110011": "PREFIX-BASED MULTICAST", # ff30::/12 [RFC3306]
|
||||
"111111110111": "RP-EMBEDDED MULTICAST", # ff70::/12 [RFC3956]
|
||||
}
|
||||
'00000000' : 'RESERVED', # ::/8
|
||||
'0' * 96 : 'RESERVED', # ::/96 Formerly IPV4COMP [RFC4291]
|
||||
'0' * 128 : 'UNSPECIFIED', # ::/128
|
||||
'0' * 127 + '1' : 'LOOPBACK', # ::1/128
|
||||
'0' * 80 + '1' * 16 : 'IPV4MAP', # ::ffff:0:0/96
|
||||
'00000000011001001111111110011011' + '0' * 64 : 'WKP46TRANS', # 0064:ff9b::/96 Well-Known-Prefix [RFC6052]
|
||||
'00000001' : 'UNASSIGNED', # 0100::/8
|
||||
'0000001' : 'RESERVED', # 0200::/7 Formerly NSAP [RFC4048]
|
||||
'0000010' : 'RESERVED', # 0400::/7 Formerly IPX [RFC3513]
|
||||
'0000011' : 'RESERVED', # 0600::/7
|
||||
'00001' : 'RESERVED', # 0800::/5
|
||||
'0001' : 'RESERVED', # 1000::/4
|
||||
'001' : 'GLOBAL-UNICAST', # 2000::/3 [RFC4291]
|
||||
'00100000000000010000000' : 'SPECIALPURPOSE', # 2001::/23 [RFC4773]
|
||||
'00100000000000010000000000000000' : 'TEREDO', # 2001::/32 [RFC4380]
|
||||
'00100000000000010000000000000010' + '0' * 16 : 'BMWG', # 2001:0002::/48 Benchmarking [RFC5180]
|
||||
'0010000000000001000000000001' : 'ORCHID', # 2001:0010::/28 (Temp until 2014-03-21) [RFC4843]
|
||||
'00100000000000010000001' : 'ALLOCATED APNIC', # 2001:0200::/23
|
||||
'00100000000000010000010' : 'ALLOCATED ARIN', # 2001:0400::/23
|
||||
'00100000000000010000011' : 'ALLOCATED RIPE NCC', # 2001:0600::/23
|
||||
'00100000000000010000100' : 'ALLOCATED RIPE NCC', # 2001:0800::/23
|
||||
'00100000000000010000101' : 'ALLOCATED RIPE NCC', # 2001:0a00::/23
|
||||
'00100000000000010000110' : 'ALLOCATED APNIC', # 2001:0c00::/23
|
||||
'00100000000000010000110110111000' : 'DOCUMENTATION', # 2001:0db8::/32 [RFC3849]
|
||||
'00100000000000010000111' : 'ALLOCATED APNIC', # 2001:0e00::/23
|
||||
'00100000000000010001001' : 'ALLOCATED LACNIC', # 2001:1200::/23
|
||||
'00100000000000010001010' : 'ALLOCATED RIPE NCC', # 2001:1400::/23
|
||||
'00100000000000010001011' : 'ALLOCATED RIPE NCC', # 2001:1600::/23
|
||||
'00100000000000010001100' : 'ALLOCATED ARIN', # 2001:1800::/23
|
||||
'00100000000000010001101' : 'ALLOCATED RIPE NCC', # 2001:1a00::/23
|
||||
'0010000000000001000111' : 'ALLOCATED RIPE NCC', # 2001:1c00::/22
|
||||
'00100000000000010010' : 'ALLOCATED RIPE NCC', # 2001:2000::/20
|
||||
'001000000000000100110' : 'ALLOCATED RIPE NCC', # 2001:3000::/21
|
||||
'0010000000000001001110' : 'ALLOCATED RIPE NCC', # 2001:3800::/22
|
||||
'0010000000000001001111' : 'RESERVED', # 2001:3c00::/22 Possible future allocation to RIPE NCC
|
||||
'00100000000000010100000' : 'ALLOCATED RIPE NCC', # 2001:4000::/23
|
||||
'00100000000000010100001' : 'ALLOCATED AFRINIC', # 2001:4200::/23
|
||||
'00100000000000010100010' : 'ALLOCATED APNIC', # 2001:4400::/23
|
||||
'00100000000000010100011' : 'ALLOCATED RIPE NCC', # 2001:4600::/23
|
||||
'00100000000000010100100' : 'ALLOCATED ARIN', # 2001:4800::/23
|
||||
'00100000000000010100101' : 'ALLOCATED RIPE NCC', # 2001:4a00::/23
|
||||
'00100000000000010100110' : 'ALLOCATED RIPE NCC', # 2001:4c00::/23
|
||||
'00100000000000010101' : 'ALLOCATED RIPE NCC', # 2001:5000::/20
|
||||
'0010000000000001100' : 'ALLOCATED APNIC', # 2001:8000::/19
|
||||
'00100000000000011010' : 'ALLOCATED APNIC', # 2001:a000::/20
|
||||
'00100000000000011011' : 'ALLOCATED APNIC', # 2001:b000::/20
|
||||
'0010000000000010' : '6TO4', # 2002::/16 "6to4" [RFC3056]
|
||||
'001000000000001100' : 'ALLOCATED RIPE NCC', # 2003::/18
|
||||
'001001000000' : 'ALLOCATED APNIC', # 2400::/12
|
||||
'001001100000' : 'ALLOCATED ARIN', # 2600::/12
|
||||
'00100110000100000000000' : 'ALLOCATED ARIN', # 2610::/23
|
||||
'00100110001000000000000' : 'ALLOCATED ARIN', # 2620::/23
|
||||
'001010000000' : 'ALLOCATED LACNIC', # 2800::/12
|
||||
'001010100000' : 'ALLOCATED RIPE NCC', # 2a00::/12
|
||||
'001011000000' : 'ALLOCATED AFRINIC', # 2c00::/12
|
||||
'00101101' : 'RESERVED', # 2d00::/8
|
||||
'0010111' : 'RESERVED', # 2e00::/7
|
||||
'0011' : 'RESERVED', # 3000::/4
|
||||
'010' : 'RESERVED', # 4000::/3
|
||||
'011' : 'RESERVED', # 6000::/3
|
||||
'100' : 'RESERVED', # 8000::/3
|
||||
'101' : 'RESERVED', # a000::/3
|
||||
'110' : 'RESERVED', # c000::/3
|
||||
'1110' : 'RESERVED', # e000::/4
|
||||
'11110' : 'RESERVED', # f000::/5
|
||||
'111110' : 'RESERVED', # f800::/6
|
||||
'1111110' : 'ULA', # fc00::/7 [RFC4193]
|
||||
'111111100' : 'RESERVED', # fe00::/9
|
||||
'1111111010' : 'LINKLOCAL', # fe80::/10
|
||||
'1111111011' : 'RESERVED', # fec0::/10 Formerly SITELOCAL [RFC4291]
|
||||
'11111111' : 'MULTICAST', # ff00::/8
|
||||
'1111111100000001' : 'NODE-LOCAL MULTICAST', # ff01::/16
|
||||
'1111111100000010' : 'LINK-LOCAL MULTICAST', # ff02::/16
|
||||
'1111111100000100' : 'ADMIN-LOCAL MULTICAST', # ff04::/16
|
||||
'1111111100000101' : 'SITE-LOCAL MULTICAST', # ff05::/16
|
||||
'1111111100001000' : 'ORG-LOCAL MULTICAST', # ff08::/16
|
||||
'1111111100001110' : 'GLOBAL MULTICAST', # ff0e::/16
|
||||
'1111111100001111' : 'RESERVED MULTICAST', # ff0f::/16
|
||||
'111111110011' : 'PREFIX-BASED MULTICAST', # ff30::/12 [RFC3306]
|
||||
'111111110111' : 'RP-EMBEDDED MULTICAST', # ff70::/12 [RFC3956]
|
||||
}
|
||||
|
||||
MAX_IPV4_ADDRESS = 0xFFFFFFFF
|
||||
MAX_IPV6_ADDRESS = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
|
||||
IPV6_TEST_MAP = 0xFFFFFFFFFFFFFFFFFFFFFFFF00000000
|
||||
IPV6_MAP_MASK = 0x00000000000000000000FFFF00000000
|
||||
MAX_IPV4_ADDRESS = 0xffffffff
|
||||
MAX_IPV6_ADDRESS = 0xffffffffffffffffffffffffffffffff
|
||||
IPV6_TEST_MAP = 0xffffffffffffffffffffffff00000000
|
||||
IPV6_MAP_MASK = 0x00000000000000000000ffff00000000
|
||||
|
||||
if sys.version_info >= (3,):
|
||||
try:
|
||||
INT_TYPES = (int, long)
|
||||
STR_TYPES = (str, unicode)
|
||||
xrange
|
||||
except NameError:
|
||||
INT_TYPES = (int,)
|
||||
STR_TYPES = (str,)
|
||||
xrange = range
|
||||
else:
|
||||
INT_TYPES = (int, long)
|
||||
STR_TYPES = (str, unicode)
|
||||
|
||||
|
||||
class IPint(object):
|
||||
|
@ -202,7 +205,7 @@ class IPint(object):
|
|||
elif isinstance(data, STR_TYPES):
|
||||
# TODO: refactor me!
|
||||
# splitting of a string into IP and prefixlen et. al.
|
||||
x = data.split("-")
|
||||
x = data.split('-')
|
||||
if len(x) == 2:
|
||||
# a.b.c.0-a.b.c.255 specification ?
|
||||
(ip, last) = x
|
||||
|
@ -219,10 +222,10 @@ class IPint(object):
|
|||
# make sure the broadcast is the same as the last ip
|
||||
# otherwise it will return /16 for something like:
|
||||
# 192.168.0.0-192.168.191.255
|
||||
if IP("%s/%s" % (ip, 32 - netbits)).broadcast().int() != last:
|
||||
if IP('%s/%s' % (ip, 32-netbits)).broadcast().int() != last:
|
||||
raise ValueError("the range %s is not on a network boundary." % data)
|
||||
elif len(x) == 1:
|
||||
x = data.split("/")
|
||||
x = data.split('/')
|
||||
# if no prefix is given use defaults
|
||||
if len(x) == 1:
|
||||
ip = x[0]
|
||||
|
@ -231,7 +234,7 @@ class IPint(object):
|
|||
raise ValueError("only one '/' allowed in IP Address")
|
||||
else:
|
||||
(ip, prefixlen) = x
|
||||
if prefixlen.find(".") != -1:
|
||||
if prefixlen.find('.') != -1:
|
||||
# check if the user might have used a netmask like
|
||||
# a.b.c.d/255.255.255.0
|
||||
(netmask, vers) = parseAddress(prefixlen)
|
||||
|
@ -255,7 +258,8 @@ class IPint(object):
|
|||
if make_net:
|
||||
self.ip = self.ip & _prefixlenToNetmask(self._prefixlen, self._ipversion)
|
||||
|
||||
if not _checkNetaddrWorksWithPrefixlen(self.ip, self._prefixlen, self._ipversion):
|
||||
if not _checkNetaddrWorksWithPrefixlen(self.ip,
|
||||
self._prefixlen, self._ipversion):
|
||||
raise ValueError("%s has invalid prefix length (%s)" % (repr(self), self._prefixlen))
|
||||
else:
|
||||
raise TypeError("Unsupported data type: %s" % type(data))
|
||||
|
@ -313,12 +317,13 @@ class IPint(object):
|
|||
want == 3 -lastip 1.2.3.0-1.2.3.255
|
||||
"""
|
||||
|
||||
if (self._ipversion == 4 and self._prefixlen == 32) or (self._ipversion == 6 and self._prefixlen == 128):
|
||||
if (self._ipversion == 4 and self._prefixlen == 32) or \
|
||||
(self._ipversion == 6 and self._prefixlen == 128):
|
||||
if self.NoPrefixForSingleIp:
|
||||
want = 0
|
||||
if want is None:
|
||||
if want == None:
|
||||
want = self.WantPrefixLen
|
||||
if want is None:
|
||||
if want == None:
|
||||
want = 1
|
||||
if want:
|
||||
if want == 2:
|
||||
|
@ -333,7 +338,7 @@ class IPint(object):
|
|||
# default
|
||||
return "/%d" % (self._prefixlen)
|
||||
else:
|
||||
return ""
|
||||
return ''
|
||||
|
||||
# We have different flavours to convert to:
|
||||
# strFullsize 127.0.0.1 2001:0658:022a:cafe:0200:c0ff:fe8d:08fa
|
||||
|
@ -342,7 +347,7 @@ class IPint(object):
|
|||
# strHex 0x7F000001 0x20010658022ACAFE0200C0FFFE8D08FA
|
||||
# strDec 2130706433 42540616829182469433547974687817795834
|
||||
|
||||
def strBin(self, wantprefixlen=None):
|
||||
def strBin(self, wantprefixlen = None):
|
||||
"""Return a string representation as a binary value.
|
||||
|
||||
>>> print(IP('127.0.0.1').strBin())
|
||||
|
@ -352,12 +357,12 @@ class IPint(object):
|
|||
"""
|
||||
|
||||
bits = _ipVersionToLen(self._ipversion)
|
||||
if self.WantPrefixLen is None and wantprefixlen is None:
|
||||
if self.WantPrefixLen == None and wantprefixlen == None:
|
||||
wantprefixlen = 0
|
||||
ret = _intToBin(self.ip)
|
||||
return "0" * (bits - len(ret)) + ret + self._printPrefix(wantprefixlen)
|
||||
return '0' * (bits - len(ret)) + ret + self._printPrefix(wantprefixlen)
|
||||
|
||||
def strCompressed(self, wantprefixlen=None):
|
||||
def strCompressed(self, wantprefixlen = None):
|
||||
"""Return a string representation in compressed format using '::' Notation.
|
||||
|
||||
>>> IP('127.0.0.1').strCompressed()
|
||||
|
@ -368,18 +373,18 @@ class IPint(object):
|
|||
'ffff:ffff:ffff:ffff:ffff:f:f:fffc/127'
|
||||
"""
|
||||
|
||||
if self.WantPrefixLen is None and wantprefixlen is None:
|
||||
if self.WantPrefixLen == None and wantprefixlen == None:
|
||||
wantprefixlen = 1
|
||||
|
||||
if self._ipversion == 4:
|
||||
return self.strFullsize(wantprefixlen)
|
||||
else:
|
||||
if self.ip >> 32 == 0xFFFF:
|
||||
if self.ip >> 32 == 0xffff:
|
||||
ipv4 = intToIp(self.ip & MAX_IPV4_ADDRESS, 4)
|
||||
text = "::ffff:" + ipv4 + self._printPrefix(wantprefixlen)
|
||||
return text
|
||||
# find the longest sequence of '0'
|
||||
hextets = [int(x, 16) for x in self.strFullsize(0).split(":")]
|
||||
hextets = [int(x, 16) for x in self.strFullsize(0).split(':')]
|
||||
# every element of followingzeros will contain the number of zeros
|
||||
# following the corresponding element of hextets
|
||||
followingzeros = [0] * 8
|
||||
|
@ -390,19 +395,19 @@ class IPint(object):
|
|||
if max(followingzeros) > 1:
|
||||
# genererate string with the longest number of zeros cut out
|
||||
# now we need hextets as strings
|
||||
hextets = [x for x in self.strNormal(0).split(":")]
|
||||
while compressionpos < len(hextets) and hextets[compressionpos] == "0":
|
||||
del hextets[compressionpos]
|
||||
hextets.insert(compressionpos, "")
|
||||
hextets = [x for x in self.strNormal(0).split(':')]
|
||||
while compressionpos < len(hextets) and hextets[compressionpos] == '0':
|
||||
del(hextets[compressionpos])
|
||||
hextets.insert(compressionpos, '')
|
||||
if compressionpos + 1 >= len(hextets):
|
||||
hextets.append("")
|
||||
hextets.append('')
|
||||
if compressionpos == 0:
|
||||
hextets = [""] + hextets
|
||||
return ":".join(hextets) + self._printPrefix(wantprefixlen)
|
||||
hextets = [''] + hextets
|
||||
return ':'.join(hextets) + self._printPrefix(wantprefixlen)
|
||||
else:
|
||||
return self.strNormal(0) + self._printPrefix(wantprefixlen)
|
||||
|
||||
def strNormal(self, wantprefixlen=None):
|
||||
def strNormal(self, wantprefixlen = None):
|
||||
"""Return a string representation in the usual format.
|
||||
|
||||
>>> print(IP('127.0.0.1').strNormal())
|
||||
|
@ -411,19 +416,21 @@ class IPint(object):
|
|||
2001:658:22a:cafe:200:0:0:1
|
||||
"""
|
||||
|
||||
if self.WantPrefixLen is None and wantprefixlen is None:
|
||||
if self.WantPrefixLen == None and wantprefixlen == None:
|
||||
wantprefixlen = 1
|
||||
|
||||
if self._ipversion == 4:
|
||||
ret = self.strFullsize(0)
|
||||
elif self._ipversion == 6:
|
||||
ret = ":".join(["%x" % x for x in [int(x, 16) for x in self.strFullsize(0).split(":")]])
|
||||
ret = ':'.join(["%x" % x for x in [int(x, 16) for x in self.strFullsize(0).split(':')]])
|
||||
else:
|
||||
raise ValueError("only IPv4 and IPv6 supported")
|
||||
|
||||
|
||||
|
||||
return ret + self._printPrefix(wantprefixlen)
|
||||
|
||||
def strFullsize(self, wantprefixlen=None):
|
||||
def strFullsize(self, wantprefixlen = None):
|
||||
"""Return a string representation in the non-mangled format.
|
||||
|
||||
>>> print(IP('127.0.0.1').strFullsize())
|
||||
|
@ -432,12 +439,12 @@ class IPint(object):
|
|||
2001:0658:022a:cafe:0200:0000:0000:0001
|
||||
"""
|
||||
|
||||
if self.WantPrefixLen is None and wantprefixlen is None:
|
||||
if self.WantPrefixLen == None and wantprefixlen == None:
|
||||
wantprefixlen = 1
|
||||
|
||||
return intToIp(self.ip, self._ipversion) + self._printPrefix(wantprefixlen)
|
||||
|
||||
def strHex(self, wantprefixlen=None):
|
||||
def strHex(self, wantprefixlen = None):
|
||||
"""Return a string representation in hex format in lower case.
|
||||
|
||||
>>> print(IP('127.0.0.1').strHex())
|
||||
|
@ -446,13 +453,13 @@ class IPint(object):
|
|||
0x20010658022acafe0200000000000001
|
||||
"""
|
||||
|
||||
if self.WantPrefixLen is None and wantprefixlen is None:
|
||||
if self.WantPrefixLen == None and wantprefixlen == None:
|
||||
wantprefixlen = 0
|
||||
|
||||
x = "0x%x" % self.ip
|
||||
x = '0x%x' % self.ip
|
||||
return x + self._printPrefix(wantprefixlen)
|
||||
|
||||
def strDec(self, wantprefixlen=None):
|
||||
def strDec(self, wantprefixlen = None):
|
||||
"""Return a string representation in decimal format.
|
||||
|
||||
>>> print(IP('127.0.0.1').strDec())
|
||||
|
@ -461,10 +468,10 @@ class IPint(object):
|
|||
42540616829182469433547762482097946625
|
||||
"""
|
||||
|
||||
if self.WantPrefixLen is None and wantprefixlen is None:
|
||||
if self.WantPrefixLen == None and wantprefixlen == None:
|
||||
wantprefixlen = 0
|
||||
|
||||
x = "%d" % self.ip
|
||||
x = '%d' % self.ip
|
||||
return x + self._printPrefix(wantprefixlen)
|
||||
|
||||
def iptype(self):
|
||||
|
@ -499,6 +506,7 @@ class IPint(object):
|
|||
return iprange[bits[:i]]
|
||||
return "unknown"
|
||||
|
||||
|
||||
def netmask(self):
|
||||
"""Return netmask as an integer.
|
||||
|
||||
|
@ -512,6 +520,7 @@ class IPint(object):
|
|||
|
||||
return ((2 ** self._prefixlen) - 1) << locallen
|
||||
|
||||
|
||||
def strNetmask(self):
|
||||
"""Return netmask as an string. Mostly useful for IPv6.
|
||||
|
||||
|
@ -543,6 +552,7 @@ class IPint(object):
|
|||
locallen = bits - self._prefixlen
|
||||
return 2 ** locallen
|
||||
|
||||
|
||||
def __nonzero__(self):
|
||||
"""All IPy objects should evaluate to true in boolean context.
|
||||
Ordinarily they do, but if handling a default route expressed as
|
||||
|
@ -579,8 +589,10 @@ class IPint(object):
|
|||
raise ValueError("Only adjacent networks can be added together.")
|
||||
ret = IP(self.int(), ipversion=self._ipversion)
|
||||
ret._prefixlen = self.prefixlen() - 1
|
||||
if not _checkNetaddrWorksWithPrefixlen(ret.ip, ret._prefixlen, ret._ipversion):
|
||||
raise ValueError("The resulting %s has invalid prefix length (%s)" % (repr(ret), ret._prefixlen))
|
||||
if not _checkNetaddrWorksWithPrefixlen(ret.ip, ret._prefixlen,
|
||||
ret._ipversion):
|
||||
raise ValueError("The resulting %s has invalid prefix length (%s)"
|
||||
% (repr(ret), ret._prefixlen))
|
||||
return ret
|
||||
|
||||
def __sub__(self, other):
|
||||
|
@ -619,6 +631,8 @@ class IPint(object):
|
|||
|
||||
return self.ip + int(key)
|
||||
|
||||
|
||||
|
||||
def __contains__(self, item):
|
||||
"""Called to implement membership test operators.
|
||||
|
||||
|
@ -645,6 +659,7 @@ class IPint(object):
|
|||
else:
|
||||
return False
|
||||
|
||||
|
||||
def overlaps(self, item):
|
||||
"""Check if two IP address ranges overlap.
|
||||
|
||||
|
@ -670,6 +685,7 @@ class IPint(object):
|
|||
else:
|
||||
return 0
|
||||
|
||||
|
||||
def __str__(self):
|
||||
"""Dispatch to the prefered String Representation.
|
||||
|
||||
|
@ -677,6 +693,7 @@ class IPint(object):
|
|||
|
||||
return self.strCompressed()
|
||||
|
||||
|
||||
def __repr__(self):
|
||||
"""Print a representation of the Object.
|
||||
|
||||
|
@ -688,7 +705,8 @@ class IPint(object):
|
|||
IP('10.0.0.0/24')
|
||||
"""
|
||||
|
||||
return "IPint('%s')" % (self.strCompressed(1))
|
||||
return("IPint('%s')" % (self.strCompressed(1)))
|
||||
|
||||
|
||||
def __cmp__(self, other):
|
||||
"""Called by comparison operations.
|
||||
|
@ -773,7 +791,7 @@ class IPint(object):
|
|||
thehash = int(-1)
|
||||
ip = self.ip
|
||||
while ip > 0:
|
||||
thehash = thehash ^ (ip & 0x7FFFFFFF)
|
||||
thehash = thehash ^ (ip & 0x7fffffff)
|
||||
ip = ip >> 32
|
||||
thehash = thehash ^ self._prefixlen
|
||||
return int(thehash)
|
||||
|
@ -807,17 +825,17 @@ class IP(IPint):
|
|||
|
||||
>>> IP('10.0.0.0/8').netmask()
|
||||
IP('255.0.0.0')
|
||||
"""
|
||||
"""
|
||||
return IP(IPint.netmask(self), ipversion=self._ipversion)
|
||||
|
||||
def _getIPv4Map(self):
|
||||
if self._ipversion != 6:
|
||||
return None
|
||||
if (self.ip >> 32) != 0xFFFF:
|
||||
if (self.ip >> 32) != 0xffff:
|
||||
return None
|
||||
ipv4 = self.ip & MAX_IPV4_ADDRESS
|
||||
if self._prefixlen != 128:
|
||||
ipv4 = "%s/%s" % (ipv4, 32 - (128 - self._prefixlen))
|
||||
ipv4 = '%s/%s' % (ipv4, 32-(128-self._prefixlen))
|
||||
return IP(ipv4, ipversion=4)
|
||||
|
||||
def reverseNames(self):
|
||||
|
@ -846,17 +864,17 @@ class IP(IPint):
|
|||
if self._ipversion == 4:
|
||||
ret = []
|
||||
# TODO: Refactor. Add support for IPint objects
|
||||
if self.len() < 2 ** 8:
|
||||
if self.len() < 2**8:
|
||||
for x in self:
|
||||
ret.append(x.reverseName())
|
||||
elif self.len() < 2 ** 16:
|
||||
for i in xrange(0, self.len(), 2 ** 8):
|
||||
elif self.len() < 2**16:
|
||||
for i in xrange(0, self.len(), 2**8):
|
||||
ret.append(self[i].reverseName()[2:])
|
||||
elif self.len() < 2 ** 24:
|
||||
for i in xrange(0, self.len(), 2 ** 16):
|
||||
elif self.len() < 2**24:
|
||||
for i in xrange(0, self.len(), 2**16):
|
||||
ret.append(self[i].reverseName()[4:])
|
||||
else:
|
||||
for i in xrange(0, self.len(), 2 ** 24):
|
||||
for i in xrange(0, self.len(), 2**24):
|
||||
ret.append(self[i].reverseName()[6:])
|
||||
return ret
|
||||
elif self._ipversion == 6:
|
||||
|
@ -868,7 +886,7 @@ class IP(IPint):
|
|||
raise NotImplementedError("can't create IPv6 reverse names at sub nibble level")
|
||||
s = list(s)
|
||||
s.reverse()
|
||||
s = ".".join(s)
|
||||
s = '.'.join(s)
|
||||
first_nibble_index = int(32 - (self._prefixlen // 4)) * 2
|
||||
return ["%s.ip6.arpa." % s[first_nibble_index:]]
|
||||
else:
|
||||
|
@ -893,34 +911,31 @@ class IP(IPint):
|
|||
|
||||
if self._ipversion == 4:
|
||||
s = self.strFullsize(0)
|
||||
s = s.split(".")
|
||||
s = s.split('.')
|
||||
s.reverse()
|
||||
first_byte_index = int(4 - (self._prefixlen // 8))
|
||||
if self._prefixlen % 8 != 0:
|
||||
nibblepart = "%s-%s" % (
|
||||
s[3 - (self._prefixlen // 8)],
|
||||
intToIp(self.ip + self.len() - 1, 4).split(".")[-1],
|
||||
)
|
||||
nibblepart += "."
|
||||
nibblepart = "%s-%s" % (s[3-(self._prefixlen // 8)], intToIp(self.ip + self.len() - 1, 4).split('.')[-1])
|
||||
nibblepart += '.'
|
||||
else:
|
||||
nibblepart = ""
|
||||
|
||||
s = ".".join(s[first_byte_index:])
|
||||
s = '.'.join(s[first_byte_index:])
|
||||
return "%s%s.in-addr.arpa." % (nibblepart, s)
|
||||
|
||||
elif self._ipversion == 6:
|
||||
ipv4 = self._getIPv4Map()
|
||||
if ipv4 is not None:
|
||||
return ipv4.reverseName()
|
||||
s = "%032x" % self.ip
|
||||
s = '%032x' % self.ip
|
||||
if self._prefixlen % 4 != 0:
|
||||
nibblepart = "%s-%x" % (s[self._prefixlen :], self.ip + self.len() - 1)
|
||||
nibblepart += "."
|
||||
nibblepart = "%s-%x" % (s[self._prefixlen:], self.ip + self.len() - 1)
|
||||
nibblepart += '.'
|
||||
else:
|
||||
nibblepart = ""
|
||||
s = list(s)
|
||||
s.reverse()
|
||||
s = ".".join(s)
|
||||
s = '.'.join(s)
|
||||
first_nibble_index = int(32 - (self._prefixlen // 4)) * 2
|
||||
return "%s%s.ip6.arpa." % (nibblepart, s[first_nibble_index:])
|
||||
else:
|
||||
|
@ -935,9 +950,9 @@ class IP(IPint):
|
|||
>>> print(IP('127.0.0.1').make_net('255.0.0.0'))
|
||||
127.0.0.0/8
|
||||
"""
|
||||
if "/" in str(netmask):
|
||||
if '/' in str(netmask):
|
||||
raise ValueError("invalid netmask (%s)" % netmask)
|
||||
return IP("%s/%s" % (self, netmask), make_net=True)
|
||||
return IP('%s/%s' % (self, netmask), make_net=True)
|
||||
|
||||
def __getitem__(self, key):
|
||||
"""Called to implement evaluation of self[key].
|
||||
|
@ -966,7 +981,7 @@ class IP(IPint):
|
|||
IP('10.0.0.0/8')
|
||||
"""
|
||||
|
||||
return "IP('%s')" % (self.strCompressed(1))
|
||||
return("IP('%s')" % (self.strCompressed(1)))
|
||||
|
||||
def get_mac(self):
|
||||
"""
|
||||
|
@ -978,15 +993,15 @@ class IP(IPint):
|
|||
"""
|
||||
if self._ipversion != 6:
|
||||
return None
|
||||
if (self.ip & 0x20000FFFF000000) != 0x20000FFFE000000:
|
||||
if (self.ip & 0x20000ffff000000) != 0x20000fffe000000:
|
||||
return None
|
||||
return "%02x:%02x:%02x:%02x:%02x:%02x" % (
|
||||
(((self.ip >> 56) & 0xFF) & 0xFD),
|
||||
(self.ip >> 48) & 0xFF,
|
||||
(self.ip >> 40) & 0xFF,
|
||||
(self.ip >> 16) & 0xFF,
|
||||
(self.ip >> 8) & 0xFF,
|
||||
self.ip & 0xFF,
|
||||
return '%02x:%02x:%02x:%02x:%02x:%02x' % (
|
||||
(((self.ip >> 56) & 0xff) & 0xfd),
|
||||
(self.ip >> 48) & 0xff,
|
||||
(self.ip >> 40) & 0xff,
|
||||
(self.ip >> 16) & 0xff,
|
||||
(self.ip >> 8) & 0xff,
|
||||
self.ip & 0xff,
|
||||
)
|
||||
|
||||
def v46map(self):
|
||||
|
@ -1001,23 +1016,25 @@ class IP(IPint):
|
|||
IP('192.168.1.1')
|
||||
"""
|
||||
if self._ipversion == 4:
|
||||
return IP(str(IPV6_MAP_MASK + self.ip) + "/%s" % (self._prefixlen + 96))
|
||||
return IP(str(IPV6_MAP_MASK + self.ip) +
|
||||
"/%s" % (self._prefixlen + 96))
|
||||
else:
|
||||
if self.ip & IPV6_TEST_MAP == IPV6_MAP_MASK:
|
||||
return IP(str(self.ip - IPV6_MAP_MASK) + "/%s" % (self._prefixlen - 96))
|
||||
raise ValueError("%s cannot be converted to an IPv4 address." % repr(self))
|
||||
return IP(str(self.ip - IPV6_MAP_MASK) +
|
||||
"/%s" % (self._prefixlen - 96))
|
||||
raise ValueError("%s cannot be converted to an IPv4 address."
|
||||
% repr(self))
|
||||
|
||||
|
||||
class IPSet(collections.MutableSet):
|
||||
class IPSet(collections_abc.MutableSet):
|
||||
def __init__(self, iterable=[]):
|
||||
# Make sure it's iterable, otherwise wrap
|
||||
if not isinstance(iterable, collections.Iterable):
|
||||
if not isinstance(iterable, collections_abc.Iterable):
|
||||
raise TypeError("'%s' object is not iterable" % type(iterable).__name__)
|
||||
|
||||
# Make sure we only accept IP objects
|
||||
for prefix in iterable:
|
||||
if not isinstance(prefix, IP):
|
||||
raise ValueError("Only IP objects can be added to an IPSet")
|
||||
raise ValueError('Only IP objects can be added to an IPSet')
|
||||
|
||||
# Store and optimize
|
||||
self.prefixes = iterable[:]
|
||||
|
@ -1026,7 +1043,7 @@ class IPSet(collections.MutableSet):
|
|||
def __contains__(self, ip):
|
||||
valid_masks = self.prefixtable.keys()
|
||||
if isinstance(ip, IP):
|
||||
# Don't dig through more-specific ranges
|
||||
#Don't dig through more-specific ranges
|
||||
ip_mask = ip._prefixlen
|
||||
valid_masks = [x for x in valid_masks if x <= ip_mask]
|
||||
for mask in sorted(valid_masks):
|
||||
|
@ -1078,20 +1095,20 @@ class IPSet(collections.MutableSet):
|
|||
return IPSet(result)
|
||||
|
||||
def __repr__(self):
|
||||
return "%s([" % self.__class__.__name__ + ", ".join(map(repr, self.prefixes)) + "])"
|
||||
return '%s([' % self.__class__.__name__ + ', '.join(map(repr, self.prefixes)) + '])'
|
||||
|
||||
def len(self):
|
||||
return sum(prefix.len() for prefix in self.prefixes)
|
||||
|
||||
def add(self, value):
|
||||
# Make sure it's iterable, otherwise wrap
|
||||
if not isinstance(value, collections.Iterable):
|
||||
if not isinstance(value, collections_abc.Iterable):
|
||||
value = [value]
|
||||
|
||||
# Check type
|
||||
for prefix in value:
|
||||
if not isinstance(prefix, IP):
|
||||
raise ValueError("Only IP objects can be added to an IPSet")
|
||||
raise ValueError('Only IP objects can be added to an IPSet')
|
||||
|
||||
# Append and optimize
|
||||
self.prefixes.extend(value)
|
||||
|
@ -1099,7 +1116,7 @@ class IPSet(collections.MutableSet):
|
|||
|
||||
def discard(self, value):
|
||||
# Make sure it's iterable, otherwise wrap
|
||||
if not isinstance(value, collections.Iterable):
|
||||
if not isinstance(value, collections_abc.Iterable):
|
||||
value = [value]
|
||||
|
||||
# This is much faster than iterating over the addresses
|
||||
|
@ -1109,7 +1126,7 @@ class IPSet(collections.MutableSet):
|
|||
# Remove
|
||||
for del_prefix in value:
|
||||
if not isinstance(del_prefix, IP):
|
||||
raise ValueError("Only IP objects can be removed from an IPSet")
|
||||
raise ValueError('Only IP objects can be removed from an IPSet')
|
||||
|
||||
# First check if this prefix contains anything in our list
|
||||
found = False
|
||||
|
@ -1129,7 +1146,7 @@ class IPSet(collections.MutableSet):
|
|||
found = False
|
||||
for i in range(len(self.prefixes)):
|
||||
if del_prefix in self.prefixes[i]:
|
||||
self.prefixes[i : i + 1] = self.prefixes[i] - del_prefix
|
||||
self.prefixes[i:i+1] = self.prefixes[i] - del_prefix
|
||||
break
|
||||
|
||||
self.optimize()
|
||||
|
@ -1160,7 +1177,7 @@ class IPSet(collections.MutableSet):
|
|||
while i < addrlen:
|
||||
# Everything that might be inside this prefix follows
|
||||
# directly behind it
|
||||
j = i + 1
|
||||
j = i+1
|
||||
while j < addrlen and self.prefixes[j] in self.prefixes[i]:
|
||||
# Mark for deletion by overwriting with None
|
||||
self.prefixes[j] = None
|
||||
|
@ -1184,7 +1201,7 @@ class IPSet(collections.MutableSet):
|
|||
# prefix length and differ only on the last bit of the prefix
|
||||
addrlen = len(self.prefixes)
|
||||
i = 0
|
||||
while i < addrlen - 1:
|
||||
while i < addrlen-1:
|
||||
j = i + 1
|
||||
|
||||
try:
|
||||
|
@ -1207,7 +1224,6 @@ class IPSet(collections.MutableSet):
|
|||
except KeyError:
|
||||
self.prefixtable[address._prefixlen] = [address]
|
||||
|
||||
|
||||
def _parseAddressIPv6(ipstr):
|
||||
"""
|
||||
Internal function used by parseAddress() to parse IPv6 address with ':'.
|
||||
|
@ -1274,16 +1290,16 @@ def _parseAddressIPv6(ipstr):
|
|||
fill_pos = len(items)
|
||||
index += 2
|
||||
continue
|
||||
pos = text.find(":")
|
||||
pos = text.find(':')
|
||||
if pos == 0:
|
||||
# Invalid IPv6, eg. '1::2:'
|
||||
raise ValueError("%r: Invalid IPv6 address" % ipstr)
|
||||
if pos != -1:
|
||||
items.append(text[:pos])
|
||||
if text[pos : pos + 2] == "::":
|
||||
if text[pos:pos+2] == "::":
|
||||
index += pos
|
||||
else:
|
||||
index += pos + 1
|
||||
index += pos+1
|
||||
|
||||
if index == len(ipstr):
|
||||
# Invalid IPv6, eg. '1::2:'
|
||||
|
@ -1292,13 +1308,13 @@ def _parseAddressIPv6(ipstr):
|
|||
items.append(text)
|
||||
break
|
||||
|
||||
if items and "." in items[-1]:
|
||||
if items and '.' in items[-1]:
|
||||
# IPv6 ending with IPv4 like '::ffff:192.168.0.1'
|
||||
if (fill_pos is not None) and not (fill_pos <= len(items) - 1):
|
||||
if (fill_pos is not None) and not (fill_pos <= len(items)-1):
|
||||
# Invalid IPv6: 'ffff:192.168.0.1::'
|
||||
raise ValueError("%r: Invalid IPv6 address: '::' after IPv4" % ipstr)
|
||||
value = parseAddress(items[-1])[0]
|
||||
items = items[:-1] + ["%04x" % (value >> 16), "%04x" % (value & 0xFFFF)]
|
||||
items = items[:-1] + ["%04x" % (value >> 16), "%04x" % (value & 0xffff)]
|
||||
|
||||
# Expand fill_pos to fill with '0'
|
||||
# ['1','2'] with fill_pos=1 => ['1', '0', '0', '0', '0', '0', '0', '2']
|
||||
|
@ -1306,7 +1322,7 @@ def _parseAddressIPv6(ipstr):
|
|||
diff = 8 - len(items)
|
||||
if diff <= 0:
|
||||
raise ValueError("%r: Invalid IPv6 address: '::' is not needed" % ipstr)
|
||||
items = items[:fill_pos] + ["0"] * diff + items[fill_pos:]
|
||||
items = items[:fill_pos] + ['0']*diff + items[fill_pos:]
|
||||
|
||||
# Here we have a list of 8 strings
|
||||
if len(items) != 8:
|
||||
|
@ -1319,7 +1335,7 @@ def _parseAddressIPv6(ipstr):
|
|||
for item in items:
|
||||
try:
|
||||
item = int(item, 16)
|
||||
error = not (0 <= item <= 0xFFFF)
|
||||
error = not(0 <= item <= 0xffff)
|
||||
except ValueError:
|
||||
error = True
|
||||
if error:
|
||||
|
@ -1328,7 +1344,6 @@ def _parseAddressIPv6(ipstr):
|
|||
index += 1
|
||||
return value
|
||||
|
||||
|
||||
def parseAddress(ipstr, ipversion=0):
|
||||
"""
|
||||
Parse a string and return the corresponding IP address (as integer)
|
||||
|
@ -1383,7 +1398,7 @@ def parseAddress(ipstr, ipversion=0):
|
|||
except ValueError:
|
||||
intval = None
|
||||
|
||||
if ipstr.startswith("0x") and hexval is not None:
|
||||
if ipstr.startswith('0x') and hexval is not None:
|
||||
if hexval > MAX_IPV6_ADDRESS:
|
||||
raise ValueError("IP Address can't be larger than %x: %x" % (MAX_IPV6_ADDRESS, hexval))
|
||||
if hexval <= MAX_IPV4_ADDRESS:
|
||||
|
@ -1391,19 +1406,19 @@ def parseAddress(ipstr, ipversion=0):
|
|||
else:
|
||||
return (hexval, 6)
|
||||
|
||||
if ipstr.find(":") != -1:
|
||||
if ipstr.find(':') != -1:
|
||||
return (_parseAddressIPv6(ipstr), 6)
|
||||
|
||||
elif len(ipstr) == 32 and hexval is not None:
|
||||
# assume IPv6 in pure hexadecimal notation
|
||||
return (hexval, 6)
|
||||
|
||||
elif ipstr.find(".") != -1 or (intval is not None and intval < 256 and ipversion != 6):
|
||||
elif ipstr.find('.') != -1 or (intval is not None and intval < 256 and ipversion != 6):
|
||||
# assume IPv4 ('127' gets interpreted as '127.0.0.0')
|
||||
bytes = ipstr.split(".")
|
||||
bytes = ipstr.split('.')
|
||||
if len(bytes) > 4:
|
||||
raise ValueError("IPv4 Address with more than 4 bytes")
|
||||
bytes += ["0"] * (4 - len(bytes))
|
||||
bytes += ['0'] * (4 - len(bytes))
|
||||
bytes = [int(x) for x in bytes]
|
||||
for x in bytes:
|
||||
if x > 255 or x < 0:
|
||||
|
@ -1433,12 +1448,12 @@ def intToIp(ip, version):
|
|||
if ip < 0:
|
||||
raise ValueError("IPs can't be negative: %d" % (ip))
|
||||
|
||||
ret = ""
|
||||
ret = ''
|
||||
if version == 4:
|
||||
if ip > MAX_IPV4_ADDRESS:
|
||||
raise ValueError("IPv4 Address can't be larger than %x: %x" % (MAX_IPV4_ADDRESS, ip))
|
||||
for l in xrange(4):
|
||||
ret = str(ip & 0xFF) + "." + ret
|
||||
ret = str(ip & 0xff) + '.' + ret
|
||||
ip = ip >> 8
|
||||
ret = ret[:-1]
|
||||
elif version == 6:
|
||||
|
@ -1448,14 +1463,13 @@ def intToIp(ip, version):
|
|||
for x in xrange(1, 33):
|
||||
ret = l[-x] + ret
|
||||
if x % 4 == 0:
|
||||
ret = ":" + ret
|
||||
ret = ':' + ret
|
||||
ret = ret[1:]
|
||||
else:
|
||||
raise ValueError("only IPv4 and IPv6 supported")
|
||||
|
||||
return ret
|
||||
|
||||
|
||||
def _ipVersionToLen(version):
|
||||
"""Return number of bits in address for a certain IP version.
|
||||
|
||||
|
@ -1489,25 +1503,10 @@ def _countFollowingZeros(l):
|
|||
return 1 + _countFollowingZeros(l[1:])
|
||||
|
||||
|
||||
_BitTable = {
|
||||
"0": "0000",
|
||||
"1": "0001",
|
||||
"2": "0010",
|
||||
"3": "0011",
|
||||
"4": "0100",
|
||||
"5": "0101",
|
||||
"6": "0110",
|
||||
"7": "0111",
|
||||
"8": "1000",
|
||||
"9": "1001",
|
||||
"a": "1010",
|
||||
"b": "1011",
|
||||
"c": "1100",
|
||||
"d": "1101",
|
||||
"e": "1110",
|
||||
"f": "1111",
|
||||
}
|
||||
|
||||
_BitTable = {'0': '0000', '1': '0001', '2': '0010', '3': '0011',
|
||||
'4': '0100', '5': '0101', '6': '0110', '7': '0111',
|
||||
'8': '1000', '9': '1001', 'a': '1010', 'b': '1011',
|
||||
'c': '1100', 'd': '1101', 'e': '1110', 'f': '1111'}
|
||||
|
||||
def _intToBin(val):
|
||||
"""Return the binary representation of an integer as string."""
|
||||
|
@ -1515,15 +1514,14 @@ def _intToBin(val):
|
|||
if val < 0:
|
||||
raise ValueError("Only positive values allowed")
|
||||
s = "%x" % val
|
||||
ret = ""
|
||||
ret = ''
|
||||
for x in s:
|
||||
ret += _BitTable[x]
|
||||
# remove leading zeros
|
||||
while ret[0] == "0" and len(ret) > 1:
|
||||
while ret[0] == '0' and len(ret) > 1:
|
||||
ret = ret[1:]
|
||||
return ret
|
||||
|
||||
|
||||
def _count1Bits(num):
|
||||
"""Find the highest bit set to 1 in an integer."""
|
||||
ret = 0
|
||||
|
@ -1532,7 +1530,6 @@ def _count1Bits(num):
|
|||
ret += 1
|
||||
return ret
|
||||
|
||||
|
||||
def _count0Bits(num):
|
||||
"""Find the highest bit set to 0 in an integer."""
|
||||
|
||||
|
@ -1575,7 +1572,7 @@ def _checkPrefix(ip, prefixlen, version):
|
|||
zbits = bits + 1
|
||||
else:
|
||||
zbits = _count0Bits(ip)
|
||||
if zbits < bits - prefixlen:
|
||||
if zbits < bits - prefixlen:
|
||||
return 0
|
||||
else:
|
||||
return 1
|
||||
|
@ -1604,7 +1601,7 @@ def _checkNetmask(netmask, masklen):
|
|||
def _checkNetaddrWorksWithPrefixlen(net, prefixlen, version):
|
||||
"""Check if a base addess of a network is compatible with a prefixlen"""
|
||||
try:
|
||||
return net & _prefixlenToNetmask(prefixlen, version) == net
|
||||
return (net & _prefixlenToNetmask(prefixlen, version) == net)
|
||||
except ValueError:
|
||||
return False
|
||||
|
||||
|
@ -1632,7 +1629,7 @@ def _prefixlenToNetmask(prefixlen, version):
|
|||
return 0
|
||||
elif prefixlen < 0:
|
||||
raise ValueError("Prefixlen must be > 0")
|
||||
return ((2 << prefixlen - 1) - 1) << (_ipVersionToLen(version) - prefixlen)
|
||||
return ((2<<prefixlen-1)-1) << (_ipVersionToLen(version) - prefixlen)
|
||||
|
||||
|
||||
def _remove_subprefix(prefix, subprefix):
|
||||
|
@ -1646,8 +1643,8 @@ def _remove_subprefix(prefix, subprefix):
|
|||
|
||||
# Start cutting in half, recursively
|
||||
prefixes = [
|
||||
IP("%s/%d" % (prefix[0], prefix._prefixlen + 1)),
|
||||
IP("%s/%d" % (prefix[int(prefix.len() / 2)], prefix._prefixlen + 1)),
|
||||
IP('%s/%d' % (prefix[0], prefix._prefixlen + 1)),
|
||||
IP('%s/%d' % (prefix[int(prefix.len() / 2)], prefix._prefixlen + 1)),
|
||||
]
|
||||
if subprefix in prefixes[0]:
|
||||
return _remove_subprefix(prefixes[0], subprefix) + IPSet([prefixes[1]])
|
||||
|
@ -1657,9 +1654,7 @@ def _remove_subprefix(prefix, subprefix):
|
|||
|
||||
if __name__ == "__main__":
|
||||
import doctest
|
||||
|
||||
failure, nbtest = doctest.testmod()
|
||||
if failure:
|
||||
import sys
|
||||
|
||||
sys.exit(1)
|
||||
|
|
|
@ -12,14 +12,13 @@ try:
|
|||
class LdapAuthenticationBackend(ModelBackend):
|
||||
|
||||
def get_LDAP_user(self, username, password, filterString):
|
||||
print('get_LDAP_user')
|
||||
print('get_LDAP_user {}'.format(username))
|
||||
try:
|
||||
server = Server(settings.LDAP_URL, port=settings.LDAP_PORT,
|
||||
use_ssl=settings.USE_SSL,get_info=ALL)
|
||||
connection = Connection(server,
|
||||
settings.LDAP_MASTER_DN,
|
||||
settings.LDAP_MASTER_PW, auto_bind=True)
|
||||
|
||||
connection.search(settings.LDAP_ROOT_DN,
|
||||
'(&({attr}={login})({filter}))'.format(
|
||||
attr=settings.LDAP_USER_UID_PREFIX,
|
||||
|
@ -31,11 +30,10 @@ try:
|
|||
return None
|
||||
specificUser = connection.response[0]
|
||||
userDn = str(specificUser.get('raw_dn'),'utf-8')
|
||||
with Connection(server,
|
||||
userDn,
|
||||
password) as con:
|
||||
with Connection(server, userDn, password) as con:
|
||||
return username
|
||||
except:
|
||||
except Exception as e:
|
||||
print("LDAP Exception: {}".format(e))
|
||||
return None
|
||||
return None
|
||||
|
||||
|
@ -50,6 +48,7 @@ try:
|
|||
if self.get_LDAP_user(username, password, settings.LDAP_SEARCH_GROUP_FILTER_ADMINS) is None:
|
||||
if self.get_LDAP_user(username, password, settings.LDAP_SEARCH_GROUP_FILTER_STAFF) is None:
|
||||
if self.get_LDAP_user(username, password, settings.LDAP_SEARCH_GROUP_FILTER_USERS) is None:
|
||||
print("User does not belong to any search group. Check LDAP_SEARCH_GROUP_FILTER in settings.")
|
||||
return None
|
||||
else:
|
||||
isStaff = True
|
||||
|
@ -62,7 +61,7 @@ try:
|
|||
attributes = UserAttributes.objects.get(user=user)
|
||||
# TODO VERIFY
|
||||
except User.DoesNotExist:
|
||||
print("authenticate-create new user")
|
||||
print("authenticate-create new user: {}".format(username))
|
||||
user = User(username=username)
|
||||
user.is_active = True
|
||||
user.is_staff = isStaff
|
||||
|
|
|
@ -268,6 +268,7 @@ LDAP_MASTER_PW = ''
|
|||
LDAP_ROOT_DN = ''
|
||||
## Queries to identify the users, i use groupOfUniqueNames on openldap
|
||||
|
||||
### PLEASE BE SURE memberOf overlay is activated on slapd
|
||||
## e.g. memberOf=cn=admins,cn=staff,cn=webvirtcloud,ou=groups,dc=kendar,dc=org
|
||||
LDAP_SEARCH_GROUP_FILTER_ADMINS = ''
|
||||
## e.g. memberOf=cn=staff,cn=webvirtcloud,ou=groups,dc=kendar,dc=org
|
||||
|
|
Loading…
Reference in a new issue