iprop: Support hierarchical iprop
This commit is contained in:
@@ -139,6 +139,12 @@ There is a keep-alive feature logged in the master's
|
||||
file (e.g.\&
|
||||
.Pa /var/heimdal/slave-stats ) .
|
||||
.Pp
|
||||
Note that hierarchical replication is supported by running
|
||||
an
|
||||
.Nm ipropd-master
|
||||
on the same KDC as an
|
||||
.Nm ipropd-slave .
|
||||
.Pp
|
||||
Supported options for
|
||||
.Nm ipropd-master :
|
||||
.Bl -tag -width Ds
|
||||
|
@@ -47,6 +47,7 @@ static int time_before_missing;
|
||||
static int time_before_gone;
|
||||
|
||||
const char *master_hostname;
|
||||
const char *pidfile_basename;
|
||||
|
||||
static krb5_socket_t
|
||||
make_signal_socket (krb5_context context)
|
||||
@@ -937,9 +938,13 @@ get_first(kadm5_server_context *server_context, int log_fd,
|
||||
|
||||
ret = kadm5_log_get_version_fd(server_context, log_fd, LOG_VERSION_FIRST,
|
||||
initial_verp, initial_timep);
|
||||
if (ret == HEIM_ERR_EOF)
|
||||
ret = kadm5_log_get_version_fd(server_context, log_fd,
|
||||
LOG_VERSION_UBER, initial_verp,
|
||||
initial_timep);
|
||||
if (ret != 0) {
|
||||
flock(log_fd, LOCK_UN);
|
||||
krb5_warnx(context, "could not read initial log entry");
|
||||
krb5_warn(context, ret, "could not read initial log entry");
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1529,8 +1534,10 @@ static struct getargs args[] = {
|
||||
"port ipropd will listen to", "port"},
|
||||
{ "detach", 0, arg_flag, &detach_from_console,
|
||||
"detach from console", NULL },
|
||||
{ "daemon-child", 0 , arg_integer, &daemon_child,
|
||||
{ "daemon-child", 0, arg_integer, &daemon_child,
|
||||
"private argument, do not use", NULL },
|
||||
{ "pidfile-basename", 0, arg_string, &pidfile_basename,
|
||||
"basename of pidfile; private argument for testing", "NAME" },
|
||||
{ "hostname", 0, arg_string, rk_UNCONST(&master_hostname),
|
||||
"hostname of master (if not same as hostname)", "hostname" },
|
||||
{ "verbose", 0, arg_flag, &verbose, NULL, NULL },
|
||||
@@ -1573,7 +1580,7 @@ main(int argc, char **argv)
|
||||
|
||||
if (detach_from_console && daemon_child == -1)
|
||||
daemon_child = roken_detach_prep(argc, argv, "--daemon-child");
|
||||
rk_pidfile(NULL);
|
||||
rk_pidfile(pidfile_basename);
|
||||
|
||||
ret = krb5_init_context(&context);
|
||||
if (ret)
|
||||
|
@@ -43,7 +43,8 @@ static krb5_log_facility *log_facility;
|
||||
static char five_min[] = "5 min";
|
||||
static char *server_time_lost = five_min;
|
||||
static int time_before_lost;
|
||||
const char *slave_str = NULL;
|
||||
static const char *slave_str;
|
||||
static const char *pidfile_basename;
|
||||
|
||||
static int
|
||||
connect_to_master (krb5_context context, const char *master,
|
||||
@@ -305,9 +306,9 @@ append_to_log_file(krb5_context context,
|
||||
}
|
||||
|
||||
static int
|
||||
receive_loop (krb5_context context,
|
||||
krb5_storage *sp,
|
||||
kadm5_server_context *server_context)
|
||||
receive_loop(krb5_context context,
|
||||
krb5_storage *sp,
|
||||
kadm5_server_context *server_context)
|
||||
{
|
||||
int ret;
|
||||
off_t left, right, off;
|
||||
@@ -316,6 +317,11 @@ receive_loop (krb5_context context,
|
||||
if (verbose)
|
||||
krb5_warnx(context, "receiving diffs");
|
||||
|
||||
ret = kadm5_log_exclusivelock(server_context);
|
||||
if (ret)
|
||||
krb5_err(context, IPROPD_RESTART, ret,
|
||||
"Failed to lock iprop log for writes");
|
||||
|
||||
/*
|
||||
* Seek to the first entry in the message from the master that is
|
||||
* past the current version of the local database.
|
||||
@@ -433,6 +439,12 @@ receive(krb5_context context,
|
||||
if (ret)
|
||||
krb5_err(context, IPROPD_RESTART_SLOW, ret, "db->close");
|
||||
|
||||
(void) kadm5_log_sharedlock(server_context);
|
||||
if (verbose)
|
||||
krb5_warnx(context, "downgraded iprop log lock to shared");
|
||||
kadm5_log_signal_master(server_context);
|
||||
if (verbose)
|
||||
krb5_warnx(context, "signaled master for hierarchical iprop");
|
||||
return ret2;
|
||||
}
|
||||
|
||||
@@ -481,6 +493,9 @@ reinit_log(krb5_context context,
|
||||
ret = kadm5_log_reinit(server_context, vno);
|
||||
if (ret)
|
||||
krb5_err(context, IPROPD_RESTART_SLOW, ret, "kadm5_log_reinit");
|
||||
(void) kadm5_log_sharedlock(server_context);
|
||||
if (verbose)
|
||||
krb5_warnx(context, "downgraded iprop log lock to shared");
|
||||
}
|
||||
|
||||
|
||||
@@ -500,6 +515,10 @@ receive_everything(krb5_context context, int fd,
|
||||
|
||||
krb5_warnx(context, "receive complete database");
|
||||
|
||||
ret = kadm5_log_exclusivelock(server_context);
|
||||
if (ret)
|
||||
krb5_err(context, IPROPD_RESTART, ret,
|
||||
"Failed to lock iprop log for writes");
|
||||
ret = asprintf(&dbname, "%s-NEW", server_context->db->hdb_name);
|
||||
if (ret == -1)
|
||||
krb5_err(context, IPROPD_RESTART, ENOMEM, "asprintf");
|
||||
@@ -673,8 +692,10 @@ static struct getargs args[] = {
|
||||
"port ipropd-slave will connect to", "port"},
|
||||
{ "detach", 0, arg_flag, &detach_from_console,
|
||||
"detach from console", NULL },
|
||||
{ "daemon-child", 0 , arg_integer, &daemon_child,
|
||||
{ "daemon-child", 0, arg_integer, &daemon_child,
|
||||
"private argument, do not use", NULL },
|
||||
{ "pidfile-basename", 0, arg_string, &pidfile_basename,
|
||||
"basename of pidfile; private argument for testing", "NAME" },
|
||||
{ "hostname", 0, arg_string, rk_UNCONST(&slave_str),
|
||||
"hostname of slave (if not same as hostname)", "hostname" },
|
||||
{ "verbose", 0, arg_flag, &verbose, NULL, NULL },
|
||||
@@ -729,7 +750,7 @@ main(int argc, char **argv)
|
||||
|
||||
if (detach_from_console && daemon_child == -1)
|
||||
daemon_child = roken_detach_prep(argc, argv, "--daemon-child");
|
||||
rk_pidfile(NULL);
|
||||
rk_pidfile(pidfile_basename);
|
||||
|
||||
ret = krb5_init_context(&context);
|
||||
if (ret)
|
||||
@@ -804,13 +825,16 @@ main(int argc, char **argv)
|
||||
if (ret)
|
||||
krb5_err (context, 1, ret, "db->open");
|
||||
|
||||
ret = kadm5_log_init (server_context);
|
||||
ret = kadm5_log_init(server_context);
|
||||
if (ret)
|
||||
krb5_err (context, 1, ret, "kadm5_log_init");
|
||||
krb5_err(context, 1, ret, "kadm5_log_init");
|
||||
(void) kadm5_log_sharedlock(server_context);
|
||||
if (verbose)
|
||||
krb5_warnx(context, "downgraded iprop log lock to shared");
|
||||
|
||||
ret = server_context->db->hdb_close (context, server_context->db);
|
||||
ret = server_context->db->hdb_close(context, server_context->db);
|
||||
if (ret)
|
||||
krb5_err (context, 1, ret, "db->close");
|
||||
krb5_err(context, 1, ret, "db->close");
|
||||
|
||||
get_creds(context, keytab_str, &ccache, master);
|
||||
|
||||
@@ -977,18 +1001,30 @@ main(int argc, char **argv)
|
||||
continue;
|
||||
}
|
||||
|
||||
/*
|
||||
* It's unclear why we open th HDB and call kadm5_log_init() here.
|
||||
*
|
||||
* We don't need it to process the log entries we receive in the
|
||||
* FOR_YOU case: we already call kadm5_log_recover() in receive() /
|
||||
* receive_loop(). Maybe it's just just in case, though at the
|
||||
* cost of synchronization with ipropd-master if we're running one
|
||||
* for hierarchical iprop.
|
||||
*/
|
||||
ret = server_context->db->hdb_open(context,
|
||||
server_context->db,
|
||||
O_RDWR | O_CREAT, 0600);
|
||||
if (ret)
|
||||
krb5_err (context, 1, ret, "db->open while handling a "
|
||||
"message from the master");
|
||||
|
||||
ret = kadm5_log_init(server_context);
|
||||
if (ret) {
|
||||
krb5_err(context, IPROPD_RESTART, ret, "kadm5_log_init while "
|
||||
"handling a message from the master");
|
||||
}
|
||||
(void) kadm5_log_sharedlock(server_context);
|
||||
if (verbose)
|
||||
krb5_warnx(context, "downgraded iprop log lock to shared");
|
||||
|
||||
ret = server_context->db->hdb_close (context, server_context->db);
|
||||
if (ret)
|
||||
krb5_err (context, 1, ret, "db->close while handling a "
|
||||
@@ -1019,6 +1055,7 @@ main(int argc, char **argv)
|
||||
krb5_warnx(context, "master sent us a full dump");
|
||||
ret = receive_everything(context, master_fd, server_context,
|
||||
auth_context);
|
||||
(void) kadm5_log_sharedlock(server_context);
|
||||
if (ret == 0) {
|
||||
ret = ihave(context, auth_context, master_fd,
|
||||
server_context->log_context.version);
|
||||
@@ -1027,6 +1064,11 @@ main(int argc, char **argv)
|
||||
connected = FALSE;
|
||||
else
|
||||
is_up_to_date(context, status_file, server_context);
|
||||
if (verbose)
|
||||
krb5_warnx(context, "downgraded iprop log lock to shared");
|
||||
kadm5_log_signal_master(server_context);
|
||||
if (verbose)
|
||||
krb5_warnx(context, "signaled master for hierarchical iprop");
|
||||
break;
|
||||
case ARE_YOU_THERE :
|
||||
if (verbose)
|
||||
|
@@ -61,7 +61,9 @@ EXPORTS
|
||||
kadm5_s_init_with_creds
|
||||
kadm5_s_chpass_principal_cond
|
||||
kadm5_s_create_principal_with_key
|
||||
kadm5_log_exclusivelock
|
||||
kadm5_log_set_version
|
||||
kadm5_log_sharedlock
|
||||
kadm5_log_signal_master
|
||||
;! kadm5_log_signal_socket
|
||||
kadm5_log_signal_socket_info ;!
|
||||
|
@@ -682,6 +682,40 @@ kadm5_log_init(kadm5_server_context *server_context)
|
||||
return log_init(server_context, LOCK_EX);
|
||||
}
|
||||
|
||||
/* Upgrade log lock to exclusive */
|
||||
kadm5_ret_t
|
||||
kadm5_log_exclusivelock(kadm5_server_context *server_context)
|
||||
{
|
||||
kadm5_log_context *log_context = &server_context->log_context;
|
||||
|
||||
if (log_context->lock_mode == LOCK_EX)
|
||||
return 0;
|
||||
if (log_context->log_fd == -1)
|
||||
return EINVAL;
|
||||
if (flock(log_context->log_fd, LOCK_EX) < 0)
|
||||
return errno;
|
||||
log_context->read_only = 0;
|
||||
log_context->lock_mode = LOCK_EX;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Downgrade log lock to shared */
|
||||
kadm5_ret_t
|
||||
kadm5_log_sharedlock(kadm5_server_context *server_context)
|
||||
{
|
||||
kadm5_log_context *log_context = &server_context->log_context;
|
||||
|
||||
if (log_context->lock_mode == LOCK_SH)
|
||||
return 0;
|
||||
if (log_context->log_fd == -1)
|
||||
return EINVAL;
|
||||
if (flock(log_context->log_fd, LOCK_SH) < 0)
|
||||
return errno;
|
||||
log_context->read_only = 1;
|
||||
log_context->lock_mode = LOCK_SH;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Open the log with an exclusive non-blocking lock */
|
||||
kadm5_ret_t
|
||||
kadm5_log_init_nb(kadm5_server_context *server_context)
|
||||
|
@@ -64,7 +64,9 @@ HEIMDAL_KAMD5_SERVER_1.0 {
|
||||
kadm5_s_init_with_creds;
|
||||
kadm5_s_chpass_principal_cond;
|
||||
kadm5_s_create_principal_with_key;
|
||||
kadm5_log_exclusivelock;
|
||||
kadm5_log_set_version;
|
||||
kadm5_log_sharedlock;
|
||||
kadm5_log_signal_master;
|
||||
kadm5_log_signal_socket;
|
||||
kadm5_log_previous;
|
||||
|
@@ -15,6 +15,7 @@ noinst_DATA = \
|
||||
krb5-bx509.conf \
|
||||
krb5-httpkadmind.conf \
|
||||
krb5-pkinit-win.conf \
|
||||
krb5-master2.conf \
|
||||
krb5-slave2.conf \
|
||||
krb5-slave.conf
|
||||
|
||||
@@ -51,6 +52,7 @@ pwport = 49191
|
||||
restport = 49192
|
||||
restport2 = 49193
|
||||
ipropport = 49194
|
||||
ipropport2 = 49195
|
||||
|
||||
if HAVE_DLOPEN
|
||||
do_dlopen = -e 's,[@]DLOPEN[@],true,g'
|
||||
@@ -70,6 +72,7 @@ do_subst = $(heim_verbose)sed $(do_dlopen) \
|
||||
-e 's,[@]restport2[@],$(restport2),g' \
|
||||
-e 's,[@]pwport[@],$(pwport),g' \
|
||||
-e 's,[@]ipropport[@],$(ipropport),g' \
|
||||
-e 's,[@]ipropport2[@],$(ipropport2),g' \
|
||||
-e 's,[@]objdir[@],$(top_builddir)/tests/kdc,g' \
|
||||
-e 's,[@]top_builddir[@],$(top_builddir),g' \
|
||||
-e 's,[@]db_type[@],$(db_type),g' \
|
||||
@@ -165,7 +168,7 @@ check-httpkadmind: check-httpkadmind.in Makefile krb5-httpkadmind.conf
|
||||
$(chmod) +x check-httpkadmind.tmp && \
|
||||
mv check-httpkadmind.tmp check-httpkadmind
|
||||
|
||||
check-iprop: check-iprop.in Makefile krb5.conf krb5-slave.conf krb5-slave2.conf
|
||||
check-iprop: check-iprop.in Makefile krb5.conf krb5-master2.conf krb5-slave.conf krb5-slave2.conf
|
||||
$(do_subst) < $(srcdir)/check-iprop.in > check-iprop.tmp && \
|
||||
$(chmod) +x check-iprop.tmp && \
|
||||
mv check-iprop.tmp check-iprop
|
||||
@@ -193,6 +196,9 @@ krb5.conf: krb5.conf.in Makefile
|
||||
$(do_subst) \
|
||||
-e 's,[@]WEAK[@],false,g' \
|
||||
-e 's,[@]dk[@],,g' \
|
||||
-e 's,[@]messages[@],messages,g' \
|
||||
-e 's,[@]ipropstats[@],iprop-stats,g' \
|
||||
-e 's,[@]signalsocket[@],signal,g' \
|
||||
-e 's,[@]kdc[@],,g' < $(srcdir)/krb5.conf.in > krb5.conf.tmp && \
|
||||
mv krb5.conf.tmp krb5.conf
|
||||
|
||||
@@ -236,6 +242,9 @@ krb5-weak.conf: krb5.conf.in Makefile
|
||||
$(do_subst) \
|
||||
-e 's,[@]WEAK[@],true,g' \
|
||||
-e 's,[@]dk[@],default_keys = aes256-cts-hmac-sha1-96:pw-salt arcfour-hmac-md5:pw-salt des3-cbc-sha1:pw-salt des:pw-salt,g' \
|
||||
-e 's,[@]messages[@],messages,g' \
|
||||
-e 's,[@]signalsocket[@],signal,g' \
|
||||
-e 's,[@]ipropstats[@],iprop-stats,g' \
|
||||
-e 's,[@]kdc[@],,g' < $(srcdir)/krb5.conf.in > krb5-weak.conf.tmp && \
|
||||
mv krb5-weak.conf.tmp krb5-weak.conf
|
||||
|
||||
@@ -243,13 +252,29 @@ krb5-slave.conf: krb5.conf.in Makefile
|
||||
$(do_subst) \
|
||||
-e 's,[@]WEAK[@],true,g' \
|
||||
-e 's,[@]dk[@],,g' \
|
||||
-e 's,[@]messages[@],messages,g' \
|
||||
-e 's,[@]signalsocket[@],signal2,g' \
|
||||
-e 's,[@]ipropstats[@],iprop-stats,g' \
|
||||
-e 's,[@]kdc[@],.slave,g' < $(srcdir)/krb5.conf.in > krb5-slave.conf.tmp && \
|
||||
mv krb5-slave.conf.tmp krb5-slave.conf
|
||||
|
||||
krb5-master2.conf: krb5.conf.in Makefile
|
||||
$(do_subst) \
|
||||
-e 's,[@]WEAK[@],true,g' \
|
||||
-e 's,[@]dk[@],,g' \
|
||||
-e 's,[@]messages[@],messages2,g' \
|
||||
-e 's,[@]signalsocket[@],signal2,g' \
|
||||
-e 's,[@]ipropstats[@],iprop-stats2,g' \
|
||||
-e 's,[@]kdc[@],.slave,g' < $(srcdir)/krb5.conf.in > krb5-master2.conf.tmp && \
|
||||
mv krb5-master2.conf.tmp krb5-master2.conf
|
||||
|
||||
krb5-slave2.conf: krb5.conf.in Makefile
|
||||
$(do_subst) \
|
||||
-e 's,[@]WEAK[@],true,g' \
|
||||
-e 's,[@]dk[@],,g' \
|
||||
-e 's,[@]messages[@],messages2,g' \
|
||||
-e 's,[@]signalsocket[@],signal3,g' \
|
||||
-e 's,[@]ipropstats[@],iprop-stats2,g' \
|
||||
-e 's,[@]kdc[@],.slave2,g' < $(srcdir)/krb5.conf.in > krb5-slave2.conf.tmp && \
|
||||
mv krb5-slave2.conf.tmp krb5-slave2.conf
|
||||
|
||||
@@ -295,6 +320,7 @@ CLEANFILES= \
|
||||
foopassword \
|
||||
foopassword.rkpty \
|
||||
iprop-stats \
|
||||
iprop-stats2 \
|
||||
iprop.keytab \
|
||||
ipropd.dumpfile \
|
||||
kdc-tester4.json \
|
||||
@@ -333,6 +359,8 @@ CLEANFILES= \
|
||||
sdigest-reply \
|
||||
server.keytab \
|
||||
signal \
|
||||
signal2 \
|
||||
signal3 \
|
||||
tempfile \
|
||||
test-rc-file.rc \
|
||||
ukt \
|
||||
|
@@ -50,6 +50,7 @@ R=TEST.H5L.SE
|
||||
|
||||
port=@port@
|
||||
ipropport=@ipropport@
|
||||
ipropport2=@ipropport2@
|
||||
|
||||
cache="FILE:${objdir}/cache.krb5"
|
||||
keytabfile=${objdir}/iprop.keytab
|
||||
@@ -59,6 +60,60 @@ kdc="${kdc} --addresses=localhost -P $port"
|
||||
kadmin="${kadmin} -r $R"
|
||||
kinit="${kinit} -c $cache ${afs_no_afslog}"
|
||||
|
||||
# We'll test iprop, and in particular, hierarchical iprop. This means we'll
|
||||
# have a setup like:
|
||||
#
|
||||
# ipropd-master -> ipropd-slave -> 2nd ipropd-master -> 2nd ipropd-slave
|
||||
|
||||
# Waiting for incremental propagation is inherently difficult because we don't
|
||||
# have a way for ipropd-slave to signal this script that it has received
|
||||
# updates. Well, it does have a way to signal a possible ipropd-master for
|
||||
# hierarchical iprop, but we don't have a way to get that signal here.
|
||||
#
|
||||
# FIXME: Add a private interface for async waiting for iprop.
|
||||
#
|
||||
# What we do is we have a set of utility functions:
|
||||
#
|
||||
# - get_iprop_ver [N] -> checks that N (default to 1) ops have made it over
|
||||
# - get_iprop_ver2 [N] -> same, but for second ipropd-slave instance
|
||||
#
|
||||
# - wait_for -> repeat a command until it succeeds or too many tries
|
||||
# - wait_for_slave [N] -> wait for N ops to make it over (calls get_iprop_ver)
|
||||
# - wait_for_slave2 [N] -> same, but for second ipropd-slave instance
|
||||
#
|
||||
# In particular the wait_for* functions busy-wait for a max amount of time,
|
||||
# with sleeps in between.
|
||||
#
|
||||
# NOTE: get_iprop_ver and get_iprop_ver2 keep hidden state.
|
||||
#
|
||||
# When first called, get_iprop_ver / get_iprop_ver2 save the current version
|
||||
# numbers. Thereafter they check that N ops have been received.
|
||||
#
|
||||
# It is critical to account for every incremental op via get_iprop_ver /
|
||||
# get_iprop_ver2, or wait_for_slave / wait_for_slave2, otherwise this test will
|
||||
# be racy and will have spurious failures!
|
||||
#
|
||||
# The pattern should be something like this:
|
||||
#
|
||||
# echo "Add host"
|
||||
# ${kadmin} -l add --random-key --use-defaults host/foo@${R} || exit 1
|
||||
# wait_for_slave
|
||||
# ^^^^^^^^^^^^^^
|
||||
# waits for 1 operation
|
||||
#
|
||||
# or
|
||||
#
|
||||
# echo "Rollover host keys"
|
||||
# ${kadmin} -l cpw -r --keepold host/foo@${R} || exit 1
|
||||
# ${kadmin} -l cpw -r --keepold host/foo@${R} || exit 1
|
||||
# ${kadmin} -l cpw -r --keepold host/foo@${R} || exit 1
|
||||
# wait_for_slave 3
|
||||
# ^^^^^^^^^^^^^^^^
|
||||
# waits for the three operations
|
||||
#
|
||||
# So though all operations must be accounted for, they need not be accounted
|
||||
# one by one.
|
||||
|
||||
slave_ver_from_master_old=
|
||||
slave_ver_from_master_new=
|
||||
slave_ver_old=
|
||||
@@ -84,6 +139,31 @@ get_iprop_ver () {
|
||||
return 0
|
||||
}
|
||||
|
||||
slave_ver_from_master_old2=
|
||||
slave_ver_from_master_new2=
|
||||
slave_ver_old2=
|
||||
slave_ver_new2=
|
||||
get_iprop_ver2 () {
|
||||
min_change=${1:-1}
|
||||
slave_ver_from_master_new2=`grep '^iprop/' iprop-stats2 | head -1 | awk '{print $3}'`
|
||||
slave_ver_new2=`grep 'up-to-date with version:' iprop-slave-status2 | awk '{print $4}'`
|
||||
if [ -z "$slave_ver_from_master_new2" -o -z "$slave_ver_new2" ]; then
|
||||
return 1
|
||||
fi
|
||||
if [ x"$slave_ver_from_master_new2" != x"$slave_ver_new2" ]; then
|
||||
return 1
|
||||
fi
|
||||
if [ x"$slave_ver_from_master_old2" != x ]; then
|
||||
change=`expr "$slave_ver_from_master_new2" - "$slave_ver_from_master_old2"`
|
||||
if [ "$change" -lt "$min_change" ]; then
|
||||
return 1
|
||||
fi
|
||||
fi
|
||||
slave_ver_from_master_old2=$slave_ver_from_master_new2
|
||||
slave_ver_old2=$slave_ver_new2
|
||||
return 0
|
||||
}
|
||||
|
||||
waitsec=65
|
||||
sleeptime=2
|
||||
wait_for () {
|
||||
@@ -119,6 +199,10 @@ wait_for_slave () {
|
||||
wait_for "iprop versions to change and/or slave to catch up" get_iprop_ver "$@"
|
||||
}
|
||||
|
||||
wait_for_slave2 () {
|
||||
wait_for "iprop versions to change and/or second slave to catch up" get_iprop_ver2 "$@"
|
||||
}
|
||||
|
||||
wait_for_master_down () {
|
||||
wait_for "master to exit" check_pidfile_is_dead ipropd-master
|
||||
}
|
||||
@@ -135,9 +219,10 @@ rm -f current-db*
|
||||
rm -f current*.log
|
||||
rm -f out-*
|
||||
rm -f mkey.file*
|
||||
rm -f messages.log
|
||||
rm -f messages.log messages.log
|
||||
|
||||
> messages.log
|
||||
> messages.log2
|
||||
|
||||
echo Creating database
|
||||
${kadmin} -l \
|
||||
@@ -194,8 +279,11 @@ ipdm=
|
||||
kdcpid=
|
||||
|
||||
> iprop-stats
|
||||
rm -f iprop-slave-status
|
||||
> iprop-stats2
|
||||
rm -f iprop-slave-status iprop-slave-status2
|
||||
|
||||
ipropd_slave2=$ipropd_slave
|
||||
ipropd_master2=$ipropd_master
|
||||
ipropd_slave="${ipropd_slave} --status-file=iprop-slave-status --port=$ipropport"
|
||||
ipropd_slave="${ipropd_slave} --hostname=slave.test.h5l.se -k ${keytab}"
|
||||
ipropd_slave="${ipropd_slave} --detach localhost"
|
||||
@@ -203,7 +291,27 @@ ipropd_master="${ipropd_master} --hostname=localhost -k ${keytab}"
|
||||
ipropd_master="${ipropd_master} --port=$ipropport"
|
||||
ipropd_master="${ipropd_master} --database=${objdir}/current-db --detach"
|
||||
|
||||
trap "echo 'killing ipropd s + m + kdc'; kill -9 \${ipdm} \${ipds} \${kdcpid} >/dev/null 2>/dev/null; tail messages.log ; tail iprop-stats; exit 1;" EXIT
|
||||
ipropd_slave2="${ipropd_slave2} --status-file=iprop-slave-status2 --port=$ipropport2"
|
||||
ipropd_slave2="${ipropd_slave2} --hostname=slave.test.h5l.se -k ${keytab}"
|
||||
ipropd_slave2="${ipropd_slave2} --pidfile-basename=ipropd-slave2"
|
||||
ipropd_slave2="${ipropd_slave2} --detach localhost"
|
||||
ipropd_master2="${ipropd_master2} --hostname=localhost -k ${keytab}"
|
||||
ipropd_master2="${ipropd_master2} --port=$ipropport2"
|
||||
ipropd_master2="${ipropd_master2} --pidfile-basename=ipropd-master2"
|
||||
ipropd_master2="${ipropd_master2} --database=${objdir}/current-db.slave --detach"
|
||||
|
||||
cleanup() {
|
||||
echo 'killing ipropd s + m + kdc'
|
||||
test -n "$ipdm" && kill -9 $ipdm >/dev/null 2>/dev/null
|
||||
test -n "$ipdm2" && kill -9 $ipdm2 >/dev/null 2>/dev/null
|
||||
test -n "$ipds" && kill -9 $ipds >/dev/null 2>/dev/null
|
||||
test -n "$ipds2" && kill -9 $ipds2 >/dev/null 2>/dev/null
|
||||
test -n "$kdcpid" && kill -9 $kdcpid >/dev/null 2>/dev/null
|
||||
tail messages.log
|
||||
tail iprop-stats
|
||||
exit 1
|
||||
}
|
||||
trap cleanup EXIT
|
||||
|
||||
echo Starting kdc ; > messages.log
|
||||
${kdc} --detach --testing || { echo "kdc failed to start"; exit 1; }
|
||||
@@ -226,6 +334,22 @@ echo "checking slave is up"
|
||||
${EGREP} 'iprop/slave.test.h5l.se@TEST.H5L.SE.*Up' iprop-stats >/dev/null || exit 1
|
||||
${EGREP} 'up-to-date with version' iprop-slave-status >/dev/null || { echo "slave to up to date" ; cat iprop-slave-status ; exit 1; }
|
||||
|
||||
# Also setup a second master on the slave, then a second slave to pull from the
|
||||
# second master.
|
||||
echo "starting master2" ; > messages.log
|
||||
env ${HEIM_MALLOC_DEBUG} \
|
||||
KRB5_CONFIG="${objdir}/krb5-master2.conf" \
|
||||
${ipropd_master2} || { echo "second ipropd-master failed to start"; exit 1; }
|
||||
ipdm2=`getpid ipropd-master2`
|
||||
|
||||
echo "starting slave2" ; > messages.log
|
||||
env ${HEIM_MALLOC_DEBUG} \
|
||||
KRB5_CONFIG="${objdir}/krb5-slave2.conf" \
|
||||
${ipropd_slave2} || { echo "ipropd-slave failed to start"; exit 1; }
|
||||
ipds2=`getpid ipropd-slave2`
|
||||
sh ${wait_kdc} ipropd-slave messages2.log 'slave status change: up-to-date' || exit 1
|
||||
wait_for "Slave sees new host" get_iprop_ver2 0 || exit 1
|
||||
|
||||
# ----------------- checking: pushing lives changes
|
||||
|
||||
slave_get() { KRB5_CONFIG="${objdir}/krb5-slave.conf" ${kadmin} -l get "$@"; }
|
||||
@@ -242,6 +366,7 @@ slave_check_exists() {
|
||||
|
||||
echo "Add host"
|
||||
${kadmin} -l add --random-key --use-defaults host/foo@${R} || exit 1
|
||||
wait_for_slave
|
||||
wait_for "Slave sees new host" slave_check_exists "host/foo@${R}"
|
||||
|
||||
echo "Rollover host keys"
|
||||
@@ -254,6 +379,8 @@ slave_get host/foo@${R} | \
|
||||
' | sed 's/^.*[[]\(.*\)[]].*$/\1/' | grep '[0-9]' | sort -nu | tr -d '
|
||||
' | ${EGREP} 1234 > /dev/null || exit 1
|
||||
|
||||
wait_for_slave2 4
|
||||
|
||||
echo "Delete 3DES keys"
|
||||
${kadmin} -l del_enctype host/foo@${R} des3-cbc-sha1
|
||||
wait_for_slave
|
||||
@@ -280,6 +407,8 @@ ${kadmin} -l get host/foo@${R} > /dev/null 2>/dev/null && exit 1
|
||||
KRB5_CONFIG="${objdir}/krb5-slave.conf" \
|
||||
${kadmin} -l get host/bar@${R} > /dev/null || exit 1
|
||||
|
||||
wait_for_slave2 3
|
||||
|
||||
echo "Delete host"
|
||||
${kadmin} -l delete host/bar@${R} || exit 1
|
||||
wait_for_slave
|
||||
@@ -290,8 +419,11 @@ ${kadmin} -l get host/bar@${R} > /dev/null 2>/dev/null && exit 1
|
||||
echo "Re-add host"
|
||||
${kadmin} -l add --random-key --use-defaults host/foo@${R} || exit 1
|
||||
${kadmin} -l add --random-key --use-defaults host/bar@${R} || exit 1
|
||||
wait_for_slave 2
|
||||
wait_for "Slave sees re-added host" slave_check_exists "host/bar@${R}"
|
||||
|
||||
wait_for_slave2 3
|
||||
|
||||
echo "kill slave and remove log and database"
|
||||
> iprop-stats
|
||||
sh ${leaks_kill} ipropd-slave $ipds || exit 1
|
||||
@@ -324,6 +456,7 @@ echo "checking slave is up again"
|
||||
wait_for "slave to start and connect to master" \
|
||||
${EGREP} 'iprop/slave.test.h5l.se@TEST.H5L.SE.*Up' iprop-stats >/dev/null
|
||||
wait_for_slave 2
|
||||
wait_for_slave2 2
|
||||
${EGREP} 'up-to-date with version' iprop-slave-status >/dev/null || { echo "slave not up to date" ; cat iprop-slave-status ; exit 1; }
|
||||
echo "checking for replay problems"
|
||||
${EGREP} 'Entry already exists in database' messages.log && exit 1
|
||||
@@ -359,6 +492,7 @@ ${EGREP} 'Entry already exists in database' messages.log && exit 1
|
||||
|
||||
${kadmin} -l cpw --random-password user@${R} > /dev/null || exit 1
|
||||
wait_for_slave
|
||||
wait_for_slave2
|
||||
|
||||
echo "live truncate on master log"
|
||||
${iprop_log} truncate -K 5 || exit 1
|
||||
@@ -408,6 +542,7 @@ ${EGREP} 'Entry already exists in database' messages.log && exit 1
|
||||
echo "pushing one change"
|
||||
${kadmin} -l cpw --random-password user@${R} > /dev/null || exit 1
|
||||
wait_for_slave
|
||||
wait_for_slave2 0
|
||||
|
||||
echo "Killing master"
|
||||
sh ${leaks_kill} ipropd-master $ipdm || exit 1
|
||||
@@ -439,6 +574,7 @@ kill -0 ${ipds} || { echo "slave no longer there"; exit 1; }
|
||||
echo "pushing one change"
|
||||
${kadmin} -l cpw --random-password user@${R} > /dev/null || exit 1
|
||||
wait_for_slave
|
||||
wait_for_slave2
|
||||
|
||||
echo "shutting down all services"
|
||||
|
||||
@@ -446,6 +582,8 @@ leaked=false
|
||||
sh ${leaks_kill} kdc $kdcpid || leaked=true
|
||||
sh ${leaks_kill} ipropd-master $ipdm || leaked=true
|
||||
sh ${leaks_kill} ipropd-slave $ipds || leaked=true
|
||||
sh ${leaks_kill} ipropd-master $ipdm2 || leaked=true
|
||||
sh ${leaks_kill} ipropd-slave $ipds2 || leaked=true
|
||||
rm -f iprop-slave-status
|
||||
trap "" EXIT
|
||||
$leaked && exit 1
|
||||
|
@@ -114,8 +114,8 @@
|
||||
}
|
||||
}
|
||||
|
||||
signal_socket = @objdir@/signal
|
||||
iprop-stats = @objdir@/iprop-stats
|
||||
signal_socket = @objdir@/@signalsocket@
|
||||
iprop-stats = @objdir@/@ipropstats@
|
||||
iprop-acl = @srcdir@/iprop-acl
|
||||
log-max-size = 40000
|
||||
|
||||
@@ -123,14 +123,14 @@
|
||||
db-dir = @objdir@
|
||||
|
||||
[logging]
|
||||
kdc = 0-/FILE:@objdir@/messages.log
|
||||
krb5 = 0-/FILE:@objdir@/messages.log
|
||||
default = 0-/FILE:@objdir@/messages.log
|
||||
kdc = 0-/FILE:@objdir@/@messages@.log
|
||||
krb5 = 0-/FILE:@objdir@/@messages@.log
|
||||
default = 0-/FILE:@objdir@/@messages@.log
|
||||
|
||||
# If you are doing preformance measurements on OSX you want to change
|
||||
# the kdc LOG line from = to - below to keep the FILE open and avoid
|
||||
# open/write/close which is blocking (rdar:// ) on OSX.
|
||||
# kdc = 0-/FILE=@objdir@/messages.log
|
||||
# kdc = 0-/FILE=@objdir@/@messages@.log
|
||||
|
||||
[kadmin]
|
||||
save-password = true
|
||||
|
Reference in New Issue
Block a user