-2010-10-17 Bob Halley <halley@dnspython.org>
+2010-10-17 Bob Halley <halley@dnspython.org>
+
+ * dns/dnssec.py: Added key_id() and make_ds().
+
+2010-10-17 Bob Halley <halley@dnspython.org>
* dns/message.py: message.py needs to import dns.edns since it uses
it.
"""Common DNSSEC-related functions and constants."""
+import dns.name
+import dns.rdata
+import dns.rdatatype
+import dns.rdataclass
+
RSAMD5 = 1
DH = 2
DSA = 3
def algorithm_from_text(text):
"""Convert text into a DNSSEC algorithm value
@rtype: int"""
-
+
value = _algorithm_by_text.get(text.upper())
if value is None:
value = int(text)
def algorithm_to_text(value):
"""Convert a DNSSEC algorithm value to text
@rtype: string"""
-
+
text = _algorithm_by_value.get(value)
if text is None:
text = str(value)
return text
+
+def _to_rdata(record):
+ s = cStringIO.StringIO()
+ record.to_wire(s)
+ return s.getvalue()
+
+def key_id(key):
+ rdata = _to_rdata(key)
+ if key.algorithm == RSAMD5:
+ return (ord(rdata[-3]) << 8) + ord(rdata[-2])
+ else:
+ total = 0
+ for i in range(len(rdata) / 2):
+ total += (ord(rdata[2 * i]) << 8) + ord(rdata[2 * i + 1])
+ if len(rdata) % 2 != 0:
+ total += ord(rdata[len(rdata) - 1]) << 8
+ total += ((total >> 16) & 0xffff);
+ return total & 0xffff
+
+def make_ds(name, key, algorithm):
+ if algorithm.upper() == 'SHA1':
+ dsalg = 1
+ hash = hashlib.sha1()
+ elif algorithm.upper() == 'SHA256':
+ dsalg = 2
+ hash = hashlib.sha256()
+ else:
+ raise ValueError, 'unsupported algorithm "%s"' % algorithm
+
+ if isinstance(name, str):
+ name = dns.name.from_text(name)
+ hash.update(name.canonicalize().to_wire())
+ hash.update(_to_rdata(key))
+ digest = hash.digest()
+
+ dsrdata = struct.pack("!HBB", key_id(key), key.algorithm, dsalg) + digest
+ return dns.rdata.from_wire(dns.rdataclass.IN, dns.rdatatype.DS, dsrdata, 0,
+ len(dsrdata))