Commit c6ccba7e authored by Michael Hanselmann's avatar Michael Hanselmann

ganeti-cleaner: Remove expired X509 certs

Importing/exporting an instance to a remote machine creates X509
certificates which expire after some time. They need to be removed from
the nodes as they become useless.
Signed-off-by: default avatarMichael Hanselmann <hansmi@google.com>
Reviewed-by: default avatarIustin Pop <iustin@google.com>
parent e9f637cb
......@@ -245,7 +245,8 @@ dist_tools_SCRIPTS = \
tools/sanitize-config
pkglib_python_scripts = \
daemons/import-export
daemons/import-export \
tools/check-cert-expired
pkglib_SCRIPTS = \
daemons/daemon-util \
......@@ -366,6 +367,7 @@ python_tests = \
dist_TESTS = \
test/daemon-util_unittest.bash \
test/import-export_unittest.bash \
test/check-cert-expired_unittest.bash \
$(python_tests)
nodist_TESTS =
......
......@@ -32,9 +32,24 @@ cleanup_master() {
xargs -r0 rm -vf
}
cleanup_node() {
# Return if directory for crypto keys doesn't exist
[[ -d $CRYPTO_DIR ]] || return 0
find $CRYPTO_DIR -mindepth 1 -maxdepth 1 -type d | \
while read dir; do
if $CHECK_CERT_EXPIRED $dir/cert; then
rm -vf $dir/{cert,key}
rmdir -v --ignore-fail-on-non-empty $dir
fi
done
}
DATA_DIR=@LOCALSTATEDIR@/lib/ganeti
CLEANER_LOG_DIR=@LOCALSTATEDIR@/log/ganeti/cleaner
QUEUE_ARCHIVE_DIR=$DATA_DIR/queue/archive
CRYPTO_DIR=@LOCALSTATEDIR@/run/ganeti/crypto
CHECK_CERT_EXPIRED=@PKGLIBDIR@/check-cert-expired
# Define how many days archived jobs should be left alone
REMOVE_AFTER=21
......@@ -58,5 +73,6 @@ find $CLEANER_LOG_DIR -maxdepth 1 -type f | sort | head -n -$KEEP_LOGS | \
xargs -r rm -vf
cleanup_master
cleanup_node
exit 0
......@@ -2,7 +2,7 @@
<!-- Fill in your name for FIRSTNAME and SURNAME. -->
<!-- Please adjust the date whenever revising the manpage. -->
<!ENTITY dhdate "<date>February 11, 2009</date>">
<!ENTITY dhdate "<date>May 17, 2010</date>">
<!-- SECTION should be 1-8, maybe w/ subsection other parameters are
allowed: see man(7), man(1). -->
<!ENTITY dhsection "<manvolnum>8</manvolnum>">
......@@ -19,6 +19,7 @@
<refentryinfo>
<copyright>
<year>2009</year>
<year>2010</year>
<holder>Google Inc.</holder>
</copyright>
&dhdate;
......@@ -45,13 +46,16 @@
<para>
The <command>&dhpackage;</command> is a periodically run script to clean
old job files from the job queue archive.
old job files from the job queue archive and to remove expired X509
certificates and keys.
</para>
<para>
<command>&dhpackage;</command> automatically removes all files older than
21 days from
<filename>@LOCALSTATEDIR@/lib/ganeti/queue/archive</filename>.
<filename>@LOCALSTATEDIR@/lib/ganeti/queue/archive</filename> and all
expired certificates and keys from
<filename>@LOCALSTATEDIR@/run/ganeti/crypto</filename>
</para>
</refsect1>
......
#!/bin/bash
#
# Copyright (C) 2010 Google Inc.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
# 02110-1301, USA.
set -e
set -o pipefail
export PYTHON=${PYTHON:=python}
CCE=tools/check-cert-expired
err() {
echo "$@"
echo 'Aborting'
exit 1
}
impexpd_helper() {
$PYTHON "${TOP_SRCDIR:-.}/test/import-export_unittest-helper" "$@"
}
$CCE 2>/dev/null && err 'Accepted empty argument list'
$CCE foo bar 2>/dev/null && err 'Accepted more than one argument'
$CCE foo bar baz 2>/dev/null && err 'Accepted more than one argument'
tmpdir=$(mktemp -d)
trap "rm -rf $tmpdir" EXIT
[[ -f "$tmpdir/cert-not" ]] && err 'File existed when it should not'
$CCE $tmpdir/cert-not 2>/dev/null && err 'Accepted non-existent file'
VALIDITY=1 impexpd_helper $tmpdir/cert-valid gencert
$CCE $tmpdir/cert-valid 2>/dev/null && \
err 'Reported valid certificate as expired'
VALIDITY=-50 impexpd_helper $tmpdir/cert-expired gencert
$CCE $tmpdir/cert-expired 2>/dev/null || \
err 'Reported expired certificate as valid'
echo > $tmpdir/cert-invalid
$CCE $tmpdir/cert-invalid 2>/dev/null && \
err 'Reported invalid certificate as expired'
echo 'Hello World' > $tmpdir/cert-invalid2
$CCE $tmpdir/cert-invalid2 2>/dev/null && \
err 'Reported invalid certificate as expired'
exit 0
......@@ -33,6 +33,7 @@ from ganeti import serializer
RETRY_INTERVAL = 0.1
TIMEOUT = int(os.getenv("TIMEOUT", 10))
VALIDITY = int(os.getenv("VALIDITY", 1))
def _GetImportExportData(filename):
......@@ -68,7 +69,7 @@ def main():
elif what == "connected":
WaitForConnected(filename)
elif what == "gencert":
utils.GenerateSelfSignedSslCert(filename, validity=1)
utils.GenerateSelfSignedSslCert(filename, validity=VALIDITY)
else:
raise Exception("Unknown command '%s'" % what)
......
#!/usr/bin/python
#
# Copyright (C) 2010 Google Inc.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
# 02110-1301, USA.
"""Tool to detect expired X509 certificates.
"""
# pylint: disable-msg=C0103
# C0103: Invalid name check-cert-expired
import os.path
import sys
import OpenSSL
from ganeti import constants
from ganeti import cli
from ganeti import utils
def main():
"""Main routine.
"""
program = os.path.basename(sys.argv[0])
if len(sys.argv) != 2:
cli.ToStderr("Usage: %s <certificate-path>", program)
sys.exit(constants.EXIT_FAILURE)
filename = sys.argv[1]
# Read certificate
try:
cert_pem = utils.ReadFile(filename)
except EnvironmentError, err:
cli.ToStderr("Unable to read %s: %s", filename, err)
sys.exit(constants.EXIT_FAILURE)
# Check validity
try:
cert = OpenSSL.crypto.load_certificate(OpenSSL.crypto.FILETYPE_PEM,
cert_pem)
(errcode, msg) = utils.VerifyX509Certificate(cert, None, None)
if msg:
cli.ToStderr("%s: %s", filename, msg)
if errcode == utils.CERT_ERROR:
sys.exit(constants.EXIT_SUCCESS)
except (KeyboardInterrupt, SystemExit):
raise
except Exception, err: # pylint: disable-msg=W0703
cli.ToStderr("Unable to check %s: %s", filename, err)
sys.exit(constants.EXIT_FAILURE)
if __name__ == "__main__":
main()
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment