summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Moss <drkjam@gmail.com>2015-08-28 23:14:52 +0100
committerDavid Moss <drkjam@gmail.com>2015-08-28 23:14:52 +0100
commit6bb599cd44230340338ffe899287edd06e055f55 (patch)
tree28c1e6e150ed693f2a44d829d50b5f673ae6b5ee
parent568ed3b8253f6b2391b295fdedf455a221bc82ee (diff)
downloadnetaddr-6bb599cd44230340338ffe899287edd06e055f55.tar.gz
Completed #109 - lookup of IPv6 unicast allocations
-rw-r--r--Makefile1
-rwxr-xr-xnetaddr/ip/iana.py123
-rw-r--r--netaddr/ip/ipv6-unicast-address-assignments.xml446
-rw-r--r--netaddr/tests/ip/test_ip_v6.py13
4 files changed, 527 insertions, 56 deletions
diff --git a/Makefile b/Makefile
index f32f70c..fd58c0c 100644
--- a/Makefile
+++ b/Makefile
@@ -51,6 +51,7 @@ download:
cd netaddr/ip/ && wget -N http://www.iana.org/assignments/ipv4-address-space/ipv4-address-space.xml
cd netaddr/ip/ && wget -N http://www.iana.org/assignments/ipv6-address-space/ipv6-address-space.xml
cd netaddr/ip/ && wget -N http://www.iana.org/assignments/multicast-addresses/multicast-addresses.xml
+ cd netaddr/ip/ && wget -N http://www.iana.org/assignments/ipv6-unicast-address-assignments/ipv6-unicast-address-assignments.xml
register:
@echo 'releasing netaddr'
diff --git a/netaddr/ip/iana.py b/netaddr/ip/iana.py
index 7e63ac1..6338ec2 100755
--- a/netaddr/ip/iana.py
+++ b/netaddr/ip/iana.py
@@ -29,22 +29,21 @@ More details can be found at the following URLs :-
- IEEE Protocols Information Home Page - http://www.iana.org/protocols/
"""
-import os as _os
import os.path as _path
import sys as _sys
-
from xml.sax import make_parser, handler
-from netaddr.core import Publisher, Subscriber, dos2unix
+from netaddr.core import Publisher, Subscriber
from netaddr.ip import IPAddress, IPNetwork, IPRange, cidr_abbrev_to_verbose
-
from netaddr.compat import _dict_items, _callable
+
#: Topic based lookup dictionary for IANA information.
IANA_INFO = {
'IPv4': {},
'IPv6': {},
+ 'IPv6_unicast': {},
'multicast': {},
}
@@ -221,6 +220,42 @@ class IPv6Parser(XMLRecordParser):
return record
+class IPv6UnicastParser(XMLRecordParser):
+ """
+ A XMLRecordParser that understands how to parse and retrieve data records
+ from the IANA IPv6 unicast address assignments file.
+
+ It can be found online here :-
+
+ - http://www.iana.org/assignments/ipv6-unicast-address-assignments/ipv6-unicast-address-assignments.xml
+ """
+ def __init__(self, fh, **kwargs):
+ """
+ Constructor.
+
+ fh - a valid, open file handle to an IANA IPv6 address space file.
+
+ kwargs - additional parser options.
+ """
+ super(IPv6UnicastParser, self).__init__(fh)
+
+ def process_record(self, rec):
+ """
+ Callback method invoked for every record.
+
+ See base class method for more details.
+ """
+ record = {
+ 'status': str(rec.get('status', '')).strip(),
+ 'description': str(rec.get('description', '')).strip(),
+ 'prefix': str(rec.get('prefix', '')).strip(),
+ 'date': str(rec.get('date', '')).strip(),
+ 'whois': str(rec.get('whois', '')).strip(),
+ }
+
+ return record
+
+
class MulticastParser(XMLRecordParser):
"""
A XMLRecordParser that knows how to process the IANA IPv4 multicast address
@@ -305,6 +340,9 @@ class DictUpdater(Subscriber):
elif self.topic == 'IPv6':
cidr = IPNetwork(cidr_abbrev_to_verbose(data_id))
self.dct[cidr] = data
+ elif self.topic == 'IPv6_unicast':
+ cidr = IPNetwork(data_id)
+ self.dct[cidr] = data
elif self.topic == 'multicast':
iprange = None
if '-' in data_id:
@@ -334,6 +372,10 @@ def load_info():
ipv6.attach(DictUpdater(IANA_INFO['IPv6'], 'IPv6', 'prefix'))
ipv6.parse()
+ ipv6ua = IPv6UnicastParser(open(_path.join(PATH, 'ipv6-unicast-address-assignments.xml')))
+ ipv6ua.attach(DictUpdater(IANA_INFO['IPv6_unicast'], 'IPv6_unicast', 'prefix'))
+ ipv6ua.parse()
+
mcast = MulticastParser(open(_path.join(PATH, 'multicast-addresses.xml')))
mcast.attach(DictUpdater(IANA_INFO['multicast'], 'multicast', 'address'))
mcast.parse()
@@ -356,77 +398,46 @@ def pprint_info(fh=None):
fh.write('%-45r' % (iprange) + details + "\n")
-def query(ip_addr):
- """
- Returns informational data specific to this IP address.
- """
- info = {}
+def _within_bounds(ip, ip_range):
+ # Boundary checking for multiple IP classes.
+ if hasattr(ip_range, 'first'):
+ # IP network or IP range.
+ return ip in ip_range
+ elif hasattr(ip_range, 'value'):
+ # IP address.
+ return ip == ip_range
+
+ raise Exception('Unsupported IP range or address: %r!' % ip_range)
- def within_bounds(ip, ip_range):
- # Boundary checking for multiple IP classes.
- if hasattr(ip_range, 'first'):
- # IP network or IP range.
- return ip in ip_range
- elif hasattr(ip_range, 'value'):
- # IP address.
- return ip == ip_range
- raise Exception('Unsupported IP range or address: %r!' % ip_range)
+def query(ip_addr):
+ """Returns informational data specific to this IP address."""
+ info = {}
if ip_addr.version == 4:
for cidr, record in _dict_items(IANA_INFO['IPv4']):
- if within_bounds(ip_addr, cidr):
+ if _within_bounds(ip_addr, cidr):
info.setdefault('IPv4', [])
info['IPv4'].append(record)
if ip_addr.is_multicast():
for iprange, record in _dict_items(IANA_INFO['multicast']):
- if within_bounds(ip_addr, iprange):
+ if _within_bounds(ip_addr, iprange):
info.setdefault('Multicast', [])
info['Multicast'].append(record)
elif ip_addr.version == 6:
for cidr, record in _dict_items(IANA_INFO['IPv6']):
- if within_bounds(ip_addr, cidr):
+ if _within_bounds(ip_addr, cidr):
info.setdefault('IPv6', [])
info['IPv6'].append(record)
- return info
+ for cidr, record in _dict_items(IANA_INFO['IPv6_unicast']):
+ if _within_bounds(ip_addr, cidr):
+ info.setdefault('IPv6_unicast', [])
+ info['IPv6_unicast'].append(record)
-
-def get_latest_files():
- """Download the latest files from IANA"""
- if _sys.version_info[0] == 3:
- # Python 3.x
- from urllib.request import Request, urlopen
- else:
- # Python 2.x
- from urllib2 import Request, urlopen
-
- urls = [
- 'http://www.iana.org/assignments/ipv4-address-space/ipv4-address-space.xml',
- 'http://www.iana.org/assignments/ipv6-address-space/ipv6-address-space.xml',
- 'http://www.iana.org/assignments/multicast-addresses/multicast-addresses.xml',
- ]
-
- for url in urls:
- _sys.stdout.write('downloading latest copy of %s\n' % url)
- request = Request(url)
- response = urlopen(request)
- save_path = _path.dirname(__file__)
- basename = _os.path.basename(response.geturl().rstrip('/'))
- filename = _path.join(save_path, basename)
- fh = open(filename, 'wb')
- fh.write(response.read())
- fh.close()
-
- # Make sure the line endings are consistent across platforms.
- dos2unix(filename)
-
-
-if __name__ == '__main__':
- # Generate indices when module is executed as a script.
- get_latest_files()
+ return info
# On module import, read IANA data files and populate lookups dict.
load_info()
diff --git a/netaddr/ip/ipv6-unicast-address-assignments.xml b/netaddr/ip/ipv6-unicast-address-assignments.xml
new file mode 100644
index 0000000..4f62e9d
--- /dev/null
+++ b/netaddr/ip/ipv6-unicast-address-assignments.xml
@@ -0,0 +1,446 @@
+<?xml version='1.0' encoding='UTF-8'?>
+<?xml-stylesheet type="text/xsl" href="ipv6-unicast-address-assignments.xsl"?>
+<?oxygen RNGSchema="ipv6-unicast-address-assignments.rng" type="xml"?>
+<registry xmlns="http://www.iana.org/assignments" id="ipv6-unicast-address-assignments">
+ <title>IPv6 Global Unicast Address Assignments</title>
+ <category>Internet Protocol version 6 (IPv6) Global Unicast Allocations</category>
+ <updated>2015-08-10</updated>
+ <xref type="rfc" data="rfc7249"/>
+ <registration_rule>Allocations to RIRs are made in line with the Global Policy published at <xref type="uri" data="http://www.icann.org/en/resources/policy/global-addressing"/>.
+All other assignments require IETF Review.</registration_rule>
+ <description>The allocation of Internet Protocol version 6 (IPv6) unicast address space is listed
+here. References to the various other registries detailing the use of the IPv6 address
+space can be found in the <xref type="registry" data="ipv6-address-space">IPv6 Address Space registry</xref>.</description>
+ <note>The assignable Global Unicast Address space is defined in <xref type="rfc" data="rfc4291"/> as being the address
+block defined by the prefix 2000::/3. All address space in this block not listed in the
+table below is reserved by IANA for future allocation.</note>
+ <record date="1999-07-01">
+ <prefix>2001:0000::/23</prefix>
+ <description>IANA</description>
+ <whois>whois.iana.org</whois>
+ <status>ALLOCATED</status>
+ <notes>2001:0000::/23 is reserved for IETF Protocol Assignments <xref type="rfc" data="rfc2928"/>.
+2001:0000::/32 is reserved for TEREDO <xref type="rfc" data="rfc4380"/>.
+2001:0002::/48 is reserved for Benchmarking <xref type="rfc" data="rfc5180"/>.
+2001:10::/28 is reserved for ORCHID <xref type="rfc" data="rfc4843"/>.
+For complete registration details, see <xref type="registry" data="iana-ipv6-special-registry"/>.</notes>
+ </record>
+ <record date="1999-07-01">
+ <prefix>2001:0000::/23</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="1999-07-01">
+ <prefix>2001:0400::/23</prefix>
+ <description>ARIN</description>
+ <whois>whois.arin.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.arin.net/registry</server>
+ <server>http://rdap.arin.net/registry</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="1999-07-01">
+ <prefix>2001:0600::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2002-05-02">
+ <prefix>2001:0800::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2002-11-02">
+ <prefix>2001:0a00::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2002-05-02">
+ <prefix>2001:0c00::/23</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes>2001:db8::/32 reserved for Documentation <xref type="rfc" data="rfc3849"/>.
+For complete registration details, see <xref type="registry" data="iana-ipv6-special-registry"/>.</notes>
+ </record>
+ <record date="2003-01-01">
+ <prefix>2001:0e00::/23</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2002-11-01">
+ <prefix>2001:1200::/23</prefix>
+ <description>LACNIC</description>
+ <whois>whois.lacnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.lacnic.net/rdap/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2003-02-01">
+ <prefix>2001:1400::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2003-07-01">
+ <prefix>2001:1600::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2003-04-01">
+ <prefix>2001:1800::/23</prefix>
+ <description>ARIN</description>
+ <whois>whois.arin.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.arin.net/registry</server>
+ <server>http://rdap.arin.net/registry</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-01-01">
+ <prefix>2001:1a00::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-05-04">
+ <prefix>2001:1c00::/22</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-05-04">
+ <prefix>2001:2000::/20</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-05-04">
+ <prefix>2001:3000::/21</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-05-04">
+ <prefix>2001:3800::/22</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record>
+ <prefix>2001:3c00::/22</prefix>
+ <description>IANA</description>
+ <whois/>
+ <status>RESERVED</status>
+ <notes>2001:3c00::/22 is reserved for possible future allocation to the RIPE NCC.</notes>
+ </record>
+ <record date="2004-06-11">
+ <prefix>2001:4000::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-06-01">
+ <prefix>2001:4200::/23</prefix>
+ <description>AFRINIC</description>
+ <whois>whois.afrinic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.afrinic.net/rdap/</server>
+ <server>http://rdap.afrinic.net/rdap/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-06-11">
+ <prefix>2001:4400::/23</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-08-17">
+ <prefix>2001:4600::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-08-24">
+ <prefix>2001:4800::/23</prefix>
+ <description>ARIN</description>
+ <whois>whois.arin.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.arin.net/registry</server>
+ <server>http://rdap.arin.net/registry</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-10-15">
+ <prefix>2001:4a00::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-12-17">
+ <prefix>2001:4c00::/23</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-09-10">
+ <prefix>2001:5000::/20</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-11-30">
+ <prefix>2001:8000::/19</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2004-11-30">
+ <prefix>2001:a000::/20</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2006-03-08">
+ <prefix>2001:b000::/20</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2001-02-01">
+ <prefix>2002:0000::/16</prefix>
+ <description>6to4</description>
+ <whois/>
+ <status>ALLOCATED</status>
+ <notes>2002::/16 is reserved for 6to4 <xref type="rfc" data="rfc3056"/>.
+For complete registration details, see <xref type="registry" data="iana-ipv6-special-registry"/>.</notes>
+ </record>
+ <record date="2005-01-12">
+ <prefix>2003:0000::/18</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2006-10-03">
+ <prefix>2400:0000::/12</prefix>
+ <description>APNIC</description>
+ <whois>whois.apnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.apnic.net/</server>
+ </rdap>
+ <notes>2400:0000::/19 was allocated on 2005-05-20. 2400:2000::/19 was allocated on 2005-07-08. 2400:4000::/21 was
+allocated on 2005-08-08. 2404:0000::/23 was allocated on 2006-01-19. The more recent allocation (2006-10-03)
+incorporates all these previous allocations.</notes>
+ </record>
+ <record date="2006-10-03">
+ <prefix>2600:0000::/12</prefix>
+ <description>ARIN</description>
+ <whois>whois.arin.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.arin.net/registry</server>
+ <server>http://rdap.arin.net/registry</server>
+ </rdap>
+ <notes>2600:0000::/22, 2604:0000::/22, 2608:0000::/22 and 260c:0000::/22 were allocated on 2005-04-19. The more
+recent allocation (2006-10-03) incorporates all these previous allocations.</notes>
+ </record>
+ <record date="2005-11-17">
+ <prefix>2610:0000::/23</prefix>
+ <description>ARIN</description>
+ <whois>whois.arin.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.arin.net/registry</server>
+ <server>http://rdap.arin.net/registry</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2006-09-12">
+ <prefix>2620:0000::/23</prefix>
+ <description>ARIN</description>
+ <whois>whois.arin.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.arin.net/registry</server>
+ <server>http://rdap.arin.net/registry</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="2006-10-03">
+ <prefix>2800:0000::/12</prefix>
+ <description>LACNIC</description>
+ <whois>whois.lacnic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.lacnic.net/rdap/</server>
+ </rdap>
+ <notes>2800:0000::/23 was allocated on 2005-11-17. The more recent allocation (2006-10-03) incorporates the
+previous allocation.</notes>
+ </record>
+ <record date="2006-10-03">
+ <prefix>2a00:0000::/12</prefix>
+ <description>RIPE NCC</description>
+ <whois>whois.ripe.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.db.ripe.net/</server>
+ </rdap>
+ <notes>2a00:0000::/21 was originally allocated on 2005-04-19. 2a01:0000::/23 was allocated on 2005-07-14.
+2a01:0000::/16 (incorporating the 2a01:0000::/23) was allocated on 2005-12-15. The more recent allocation
+(2006-10-03) incorporates these previous allocations.</notes>
+ </record>
+ <record date="2006-10-03">
+ <prefix>2c00:0000::/12</prefix>
+ <description>AFRINIC</description>
+ <whois>whois.afrinic.net</whois>
+ <status>ALLOCATED</status>
+ <rdap>
+ <server>https://rdap.afrinic.net/rdap/</server>
+ <server>http://rdap.afrinic.net/rdap/</server>
+ </rdap>
+ <notes/>
+ </record>
+ <record date="1999-07-01">
+ <prefix>2d00:0000::/8</prefix>
+ <description>IANA</description>
+ <whois/>
+ <status>RESERVED</status>
+ <notes/>
+ </record>
+ <record date="1999-07-01">
+ <prefix>2e00:0000::/7</prefix>
+ <description>IANA</description>
+ <whois/>
+ <status>RESERVED</status>
+ <notes/>
+ </record>
+ <record date="1999-07-01">
+ <prefix>3000:0000::/4</prefix>
+ <description>IANA</description>
+ <whois/>
+ <status>RESERVED</status>
+ <notes/>
+ </record>
+ <record date="2008-04">
+ <prefix>3ffe::/16</prefix>
+ <description>IANA</description>
+ <whois/>
+ <status>RESERVED</status>
+ <notes>3ffe:831f::/32 was used for Teredo in some old but widely distributed networking stacks. This usage is
+deprecated in favor of 2001::/32, which was allocated for the purpose in <xref type="rfc" data="rfc4380"/>.
+3ffe::/16 and 5f00::/8 were used for the 6bone but were returned. <xref type="rfc" data="rfc5156"/></notes>
+ </record>
+ <record date="2008-04">
+ <prefix>5f00::/8</prefix>
+ <description>IANA</description>
+ <whois/>
+ <status>RESERVED</status>
+ <notes>3ffe::/16 and 5f00::/8 were used for the 6bone but were returned. <xref type="rfc" data="rfc5156"/></notes>
+ </record>
+ <people/>
+</registry>
diff --git a/netaddr/tests/ip/test_ip_v6.py b/netaddr/tests/ip/test_ip_v6.py
index 2744844..fb19f19 100644
--- a/netaddr/tests/ip/test_ip_v6.py
+++ b/netaddr/tests/ip/test_ip_v6.py
@@ -118,3 +118,16 @@ def test_ipnetwork_pickling_v6():
assert cidr2.value == 281473902969344
assert cidr2.prefixlen == 120
assert cidr2.version == 6
+
+
+def test_ipv6_unicast_address_allocation_info():
+ ip = IPNetwork('2001:1200::/23')
+
+ assert ip.info.IPv6[0].allocation == 'Global Unicast'
+ assert ip.info.IPv6[0].prefix == '2000::/3'
+ assert ip.info.IPv6[0].reference == 'rfc4291'
+
+ assert ip.info.IPv6_unicast[0].prefix == '2001:1200::/23'
+ assert ip.info.IPv6_unicast[0].description == 'LACNIC'
+ assert ip.info.IPv6_unicast[0].whois == 'whois.lacnic.net'
+ assert ip.info.IPv6_unicast[0].status == 'ALLOCATED'