summaryrefslogtreecommitdiff
path: root/tools/readconfig.py
diff options
context:
space:
mode:
Diffstat (limited to 'tools/readconfig.py')
-rw-r--r--tools/readconfig.py54
1 files changed, 54 insertions, 0 deletions
diff --git a/tools/readconfig.py b/tools/readconfig.py
new file mode 100644
index 0000000..5079691
--- /dev/null
+++ b/tools/readconfig.py
@@ -0,0 +1,54 @@
+import io
+import ecdsa
+import hashlib
+import yaml
+import base64
+import sys
+
+class ErrorHandlingDict(dict):
+ def __init__(self, filename, path):
+ self._filename = filename
+ self._path = path
+ dict.__init__({})
+ def __missing__(self, key):
+ if self._path:
+ path = ", ".join(self._path)
+ else:
+ path = "the top level"
+ print >>sys.stderr, "error: could not find configuration key '%s' at %s in %s" % (key, path, self._filename)
+ sys.exit(1)
+
+def errorhandlify(term, filename, path=[]):
+ if isinstance(term, basestring):
+ return term
+ elif isinstance(term, int):
+ return term
+ elif isinstance(term, dict):
+ result = ErrorHandlingDict(filename, path)
+ for k, v in term.items():
+ result[k] = errorhandlify(v, filename, path + [k])
+ return result
+ elif isinstance(term, list):
+ return [errorhandlify(e, filename, path + ["item %d" % i]) for i, e in enumerate(term, start=1)]
+ else:
+ print "unknown type", type(term)
+ sys.exit(1)
+
+def verify_and_read_config(filename, publickey_base64):
+ rawconfig = open(filename).read()
+ signature = open(filename + ".sig").read()
+
+ publickey = base64.decodestring(publickey_base64)
+
+ try:
+ vk = ecdsa.VerifyingKey.from_der(publickey)
+ vk.verify(signature, rawconfig, hashfunc=hashlib.sha256,
+ sigdecode=ecdsa.util.sigdecode_der)
+ except ecdsa.keys.BadSignatureError:
+ print >>sys.stderr, "error: configuration file %s did not have a correct signature" % (filename,)
+ sys.exit(1)
+
+ return errorhandlify(yaml.load(io.BytesIO(rawconfig), yaml.SafeLoader), filename)
+
+def read_config(filename):
+ return errorhandlify(yaml.load(open(filename), yaml.SafeLoader), filename)