summaryrefslogtreecommitdiff
path: root/tools
diff options
context:
space:
mode:
authorMagnus Ahltorp <map@kth.se>2017-01-27 16:11:11 +0100
committerLinus Nordberg <linus@nordu.net>2017-02-01 10:46:27 +0100
commitc0d8aceccb0961a25ee58a163441bbcbe6d6ea3d (patch)
tree90c98ad5f286a2475c1dd04ca7ddd70df6669aea /tools
parent50667bc5c4896557415ab28269d2aea3ac534bf4 (diff)
Verify config file signature
Read log key from config file in more places. Check STH signature in storagegc.py
Diffstat (limited to 'tools')
-rwxr-xr-xtools/compileconfig.py10
-rwxr-xr-xtools/loginfo.py5
-rwxr-xr-xtools/merge_sth.py3
-rw-r--r--tools/mergetools.py6
-rw-r--r--tools/readconfig.py54
-rwxr-xr-xtools/storagegc.py7
6 files changed, 71 insertions, 14 deletions
diff --git a/tools/compileconfig.py b/tools/compileconfig.py
index 0ee3fab..b5e5053 100755
--- a/tools/compileconfig.py
+++ b/tools/compileconfig.py
@@ -5,7 +5,7 @@
import argparse
import sys
-import yaml
+import readconfig
import re
import base64
@@ -405,7 +405,6 @@ def gen_testmakefile(config, testmakefile, machines, shellvars=False):
configfile.close()
-
def main():
parser = argparse.ArgumentParser(description="")
parser.add_argument('--config', help="System configuration", required=True)
@@ -415,13 +414,16 @@ def main():
parser.add_argument("--machines", type=int, metavar="n", help="Number of machines")
args = parser.parse_args()
- config = yaml.load(open(args.config))
if args.testmakefile and args.machines:
+ config = readconfig.read_config(args.config)
gen_testmakefile(config, args.testmakefile, args.machines)
elif args.testshellvars and args.machines:
+ config = readconfig.read_config(args.config)
gen_testmakefile(config, args.testshellvars, args.machines, shellvars=True)
elif args.localconfig:
- localconfig = yaml.load(open(args.localconfig))
+ localconfig = readconfig.read_config(args.localconfig)
+ config = readconfig.verify_and_read_config(args.config, localconfig["logadminkey"])
+
localnodes = localconfig["localnodes"]
for localnode in localnodes:
gen_config(localnode, config, localconfig)
diff --git a/tools/loginfo.py b/tools/loginfo.py
index c61ad1b..1537c5e 100755
--- a/tools/loginfo.py
+++ b/tools/loginfo.py
@@ -6,7 +6,7 @@
import sys
import argparse
-import yaml
+import readconfig
from certtools import create_ssl_context, get_sth
def main():
@@ -26,8 +26,7 @@ def main():
required=True)
parser.add_argument('baseurl', help="Log base URL")
args = parser.parse_args()
- #config = yaml.load(open(args.config))
- localconfig = yaml.load(open(args.localconfig))
+ localconfig = readconfig.read_config(args.localconfig)
paths = localconfig["paths"]
create_ssl_context(cafile=paths["https_cacertfile"])
diff --git a/tools/merge_sth.py b/tools/merge_sth.py
index 6b1bb60..2bc19dd 100755
--- a/tools/merge_sth.py
+++ b/tools/merge_sth.py
@@ -12,6 +12,7 @@ import json
import urllib2
import time
import requests
+import base64
from base64 import b64encode
from mergetools import parse_args, get_nfetched, hexencode, hexdecode, \
get_logorder, get_sth
@@ -31,7 +32,7 @@ def merge_sth(args, config, localconfig):
sthfile = mergedb + "/sth"
logorderfile = mergedb + "/logorder"
currentsizefile = mergedb + "/fetched"
- logpublickey = get_public_key_from_file(paths["logpublickey"])
+ logpublickey = base64.decodestring(config["logpublickey"])
backupquorum = config.get("backup-quorum-size", 0)
assert backupquorum <= len(mergenodes) - 1
create_ssl_context(cafile=paths["https_cacertfile"])
diff --git a/tools/mergetools.py b/tools/mergetools.py
index f49e789..0afec24 100644
--- a/tools/mergetools.py
+++ b/tools/mergetools.py
@@ -7,7 +7,7 @@ import hashlib
import sys
import struct
import json
-import yaml
+import readconfig
import argparse
import requests
try:
@@ -430,8 +430,8 @@ def parse_args():
help="Print timing information")
args = parser.parse_args()
- config = yaml.load(open(args.config))
- localconfig = yaml.load(open(args.localconfig))
+ localconfig = readconfig.read_config(args.localconfig)
+ config = readconfig.verify_and_read_config(args.config, localconfig["logadminkey"])
set_api_keys(config)
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)
diff --git a/tools/storagegc.py b/tools/storagegc.py
index 38b5379..6360495 100755
--- a/tools/storagegc.py
+++ b/tools/storagegc.py
@@ -9,7 +9,7 @@ import urllib
import json
import base64
import sys
-import yaml
+import readconfig
from certtools import *
parser = argparse.ArgumentParser(description='')
@@ -17,8 +17,8 @@ parser.add_argument('--config', help="System configuration", required=True)
parser.add_argument('--localconfig', help="Local configuration", required=True)
args = parser.parse_args()
-config = yaml.load(open(args.config))
-localconfig = yaml.load(open(args.localconfig))
+localconfig = readconfig.read_config(args.localconfig)
+config = readconfig.verify_and_read_config(args.config, localconfig["logadminkey"])
paths = localconfig["paths"]
db_path = paths["db"]
@@ -27,6 +27,7 @@ create_ssl_context(cafile=paths.get("public_cacertfile", None))
baseurl = config["baseurl"]
sth = get_sth(baseurl)
+check_sth_signature(baseurl, sth, base64.decodestring(config["logpublickey"]))
def verifyleafhash(leaf_hash):
try: