From 60972e173f24cb34ab6f01a6b89e893510bc3ecd Mon Sep 17 00:00:00 2001 From: Nalin Dahyabhai Date: Oct 11 2011 17:23:56 +0000 Subject: - adjust CA polling and monitor-next-check timeouts to better handle certificates with imminent not-valid-after dates --- diff --git a/configure.ac b/configure.ac index b8ebc76..2ceaa14 100644 --- a/configure.ac +++ b/configure.ac @@ -355,6 +355,9 @@ AC_DEFINE_UNQUOTED(CM_DEFAULT_NOTIFICATION_SYSLOG_PRIORITY,"$CM_DEFAULT_NOTIFICA AC_DEFINE(CM_DELAY_SOON,5,[Define to the time to wait for something that will happen soon.]) AC_DEFINE(CM_DELAY_SOONISH,30,[Define to the time to wait for something that will happen soon, but not that soon.]) AC_DEFINE(CM_DELAY_CA_POLL,(7 * 24 * 60 * 60),[Define to the time to wait between attempts to see if the CA issued a certificate.]) +AC_DEFINE(CM_DELAY_CA_POLL_MINIMUM,(5 * 60),[Define to the absolute minimum time to wait between attempts to see if the CA issued a certificate.]) +AC_DEFINE(CM_DELAY_MONITOR_POLL,(24 * 60 * 60),[Define to the time to wait between attempts to re-read a certificate and check for expiration.]) +AC_DEFINE(CM_DELAY_MONITOR_POLL_MINIMUM,(30 * 60),[Define to the absolute minimum time to wait between attempts to re-read a certificate and check for expiration.]) AC_DEFINE(CM_DELAY_NETLINK,(60),[Define to the time to wait after a netlink routing notification to retry submissions.]) CM_SELF_SIGN_CA_NAME=SelfSign diff --git a/src/iterate.c b/src/iterate.c index d9d9a8f..dcf7458 100644 --- a/src/iterate.c +++ b/src/iterate.c @@ -177,6 +177,36 @@ cm_waitfor_readable_fd(int fd, int delay) select(fd + 1, &fds, NULL, &fds, (delay >= 0) ? &tv : NULL); } +/* Decide how long to wait before contacting the CA again. */ +static time_t +cm_decide_ca_delay(time_t remaining) +{ + time_t delay; + delay = CM_DELAY_CA_POLL; + if ((remaining != (time_t) -1) && (remaining < delay)) { + delay = remaining / 2; + if (delay < CM_DELAY_CA_POLL_MINIMUM) { + delay = CM_DELAY_CA_POLL_MINIMUM; + } + } + return delay; +} + +/* Decide how long to wait before looking at a certificate again. */ +static time_t +cm_decide_monitor_delay(time_t remaining) +{ + time_t delay; + delay = CM_DELAY_MONITOR_POLL; + if ((remaining != (time_t) -1) && (remaining < delay)) { + delay = remaining / 2; + if (delay < CM_DELAY_MONITOR_POLL_MINIMUM) { + delay = CM_DELAY_MONITOR_POLL_MINIMUM; + } + } + return delay; +} + /* Set up run-time data associated with the entry. */ int cm_iterate_init(struct cm_store_entry *entry, void **cm_iterate_state) @@ -286,6 +316,7 @@ cm_iterate(struct cm_store_entry *entry, struct cm_store_ca *ca, enum cm_time *when, int *delay, int *readfd) { int i, j; + time_t remaining; struct cm_iterate_state *state; struct cm_store_ca *tmp_ca; enum cm_state old_entry_state; @@ -295,7 +326,14 @@ cm_iterate(struct cm_store_entry *entry, struct cm_store_ca *ca, *readfd = -1; *when = cm_time_no_time; *delay = 0; + old_entry_state = entry->cm_state; + if (entry->cm_cert_not_after != 0) { + remaining = entry->cm_cert_not_after - time(NULL); + } else { + remaining = -1; + } + switch (entry->cm_state) { case CM_NEED_KEY_PAIR: /* Start a helper. */ @@ -595,8 +633,7 @@ cm_iterate(struct cm_store_entry *entry, struct cm_store_ca *ca, *when = cm_time_soonish; } else { entry->cm_state = CM_CA_REJECTED; - *when = cm_time_delay; - *delay = CM_DELAY_CA_POLL; + *when = cm_time_now; } } else if (cm_submit_unreachable(entry, @@ -606,7 +643,7 @@ cm_iterate(struct cm_store_entry *entry, struct cm_store_ca *ca, state->cm_submit_state = NULL; entry->cm_state = CM_CA_UNREACHABLE; *when = cm_time_delay; - *delay = CM_DELAY_CA_POLL; + *delay = cm_decide_ca_delay(remaining); } else if (cm_submit_save_ca_cookie(entry, state->cm_submit_state) == 0) { @@ -615,7 +652,8 @@ cm_iterate(struct cm_store_entry *entry, struct cm_store_ca *ca, cm_submit_done(entry, state->cm_submit_state); state->cm_submit_state = NULL; entry->cm_state = CM_CA_WORKING; - *when = cm_time_soonish; + *when = cm_time_delay; + *delay = cm_decide_ca_delay(remaining); } else if (cm_submit_unconfigured(entry, state->cm_submit_state) == 0) { @@ -632,7 +670,7 @@ cm_iterate(struct cm_store_entry *entry, struct cm_store_ca *ca, } else { entry->cm_state = CM_CA_UNCONFIGURED; *when = cm_time_delay; - *delay = CM_DELAY_CA_POLL; + *delay = cm_decide_ca_delay(remaining); } } else { /* Don't know what's going on. HELP! */ @@ -783,8 +821,8 @@ cm_iterate(struct cm_store_entry *entry, struct cm_store_ca *ca, *when = cm_time_now; } else { /* Nothing to do here. Check again tomorrow. */ - *delay = 24 * 60 * 60; *when = cm_time_delay; + *delay = cm_decide_monitor_delay(remaining); } break; diff --git a/tests/010-iterate/expected.out b/tests/010-iterate/expected.out index 77821d3..8fceaa1 100644 --- a/tests/010-iterate/expected.out +++ b/tests/010-iterate/expected.out @@ -167,6 +167,7 @@ HAVE_CSR -START- NEED_TO_SUBMIT SUBMITTING +delay=604800 CA_WORKING -STOP- HAVE_CSR @@ -217,6 +218,7 @@ HAVE_CSR -START- NEED_TO_SUBMIT SUBMITTING +delay=604800 CA_UNREACHABLE -STOP- HAVE_CSR @@ -242,10 +244,317 @@ HAVE_CSR -START- NEED_TO_SUBMIT SUBMITTING +delay=604800 CA_UNCONFIGURED -STOP- HAVE_CSR -START- NEED_TO_SUBMIT -STOP- + +[CA poll timeout remaining=0.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=300 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=0.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=300 +CA_WORKING +-STOP- + +[CA poll timeout remaining=0.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=300 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=0.] +MONITORING +-START- +delay=1800 +MONITORING +-STOP- + +[CA poll timeout remaining=30.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=300 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=30.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=300 +CA_WORKING +-STOP- + +[CA poll timeout remaining=30.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=300 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=30.] +MONITORING +-START- +delay=1800 +MONITORING +-STOP- + +[CA poll timeout remaining=1800.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=900 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=1800.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=900 +CA_WORKING +-STOP- + +[CA poll timeout remaining=1800.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=900 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=1800.] +MONITORING +-START- +delay=1800 +MONITORING +-STOP- + +[CA poll timeout remaining=3600.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=1800 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=3600.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=1800 +CA_WORKING +-STOP- + +[CA poll timeout remaining=3600.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=1800 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=3600.] +MONITORING +-START- +delay=1800 +MONITORING +-STOP- + +[CA poll timeout remaining=7200.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=3600 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=7200.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=3600 +CA_WORKING +-STOP- + +[CA poll timeout remaining=7200.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=3600 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=7200.] +MONITORING +-START- +delay=3600 +MONITORING +-STOP- + +[CA poll timeout remaining=86000.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=43000 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=86000.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=43000 +CA_WORKING +-STOP- + +[CA poll timeout remaining=86000.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=43000 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=86000.] +MONITORING +-START- +delay=43000 +MONITORING +-STOP- + +[CA poll timeout remaining=86500.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=43250 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=86500.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=43250 +CA_WORKING +-STOP- + +[CA poll timeout remaining=86500.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=43250 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=86500.] +MONITORING +-START- +delay=86400 +MONITORING +-STOP- + +[CA poll timeout remaining=604800.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=604800 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=604800.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=604800 +CA_WORKING +-STOP- + +[CA poll timeout remaining=604800.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=604800 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=604800.] +MONITORING +-START- +delay=86400 +MONITORING +-STOP- + +[CA poll timeout remaining=1000000.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=604800 +CA_UNREACHABLE +-STOP- + +[CA poll timeout remaining=1000000.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=604800 +CA_WORKING +-STOP- + +[CA poll timeout remaining=1000000.] +HAVE_CSR +-START- +NEED_TO_SUBMIT +SUBMITTING +delay=604800 +CA_UNCONFIGURED +-STOP- + +[Monitor poll timeout remaining=1000000.] +MONITORING +-START- +delay=86400 +MONITORING +-STOP- Test complete. diff --git a/tests/010-iterate/run.sh b/tests/010-iterate/run.sh index 4ffdf3a..f32e4f7 100755 --- a/tests/010-iterate/run.sh +++ b/tests/010-iterate/run.sh @@ -110,6 +110,7 @@ if test "`grep ^state entry`" != state=NEED_KEY_PAIR ; then exit 1 fi + echo echo '[Picking up mid-life without a certificate.]' cat > entry << EOF @@ -144,6 +145,7 @@ if test "`grep ^state entry`" != state=MONITORING ; then exit 1 fi + echo echo '[Retroactive issuing.]' cat > entry2 << EOF @@ -171,6 +173,7 @@ echo echo '[Noticing expiration.]' openssl x509 -noout -startdate -enddate -in $tmpdir/certfile2 $toolsdir/iterate ca entry2 NEED_TO_NOTIFY,NOTIFYING | sed 's@'"$tmpdir"'@$tmpdir@g' + echo echo '[Kicking off autorenew.]' cat > entry2 << EOF @@ -187,6 +190,7 @@ notification_method=STDOUT EOF openssl x509 -noout -startdate -enddate -in $tmpdir/certfile2 $toolsdir/iterate ca entry2 NEED_TO_NOTIFY,NOTIFYING | sed 's@'"$tmpdir"'@$tmpdir@g' + echo echo '[Enroll until we notice we have no specified CA.]' cat > entry3 << EOF @@ -203,6 +207,7 @@ EOF $toolsdir/iterate ca3 entry3 NEED_KEYINFO,READING_KEYINFO,HAVE_KEYINFO $toolsdir/iterate ca3 entry3 NEED_CSR,GENERATING_CSR $toolsdir/iterate ca3 entry3 NEED_TO_SUBMIT,SUBMITTING + echo echo '[Enroll until the CA tells us to come back later.]' cat > entry3 << EOF @@ -221,6 +226,7 @@ $toolsdir/iterate ca3 entry3 NEED_KEYINFO,READING_KEYINFO,HAVE_KEYINFO $toolsdir/iterate ca3 entry3 NEED_CSR,GENERATING_CSR $toolsdir/iterate ca3 entry3 NEED_TO_SUBMIT,SUBMITTING $toolsdir/iterate ca3 entry3 "" + echo echo '[Enroll until the CA rejects us.]' cat > entry3 << EOF @@ -239,6 +245,7 @@ $toolsdir/iterate ca3 entry3 NEED_KEYINFO,READING_KEYINFO,HAVE_KEYINFO $toolsdir/iterate ca3 entry3 NEED_CSR,GENERATING_CSR $toolsdir/iterate ca3 entry3 NEED_TO_SUBMIT,SUBMITTING $toolsdir/iterate ca3 entry3 "" + echo echo '[Enroll until the CA turns out to be unreachable.]' cat > entry3 << EOF @@ -257,6 +264,7 @@ $toolsdir/iterate ca3 entry3 NEED_KEYINFO,READING_KEYINFO,HAVE_KEYINFO $toolsdir/iterate ca3 entry3 NEED_CSR,GENERATING_CSR $toolsdir/iterate ca3 entry3 NEED_TO_SUBMIT,SUBMITTING $toolsdir/iterate ca3 entry3 "" + echo echo '[Enroll until the CA client turns out to be unconfigured.]' cat > entry3 << EOF @@ -275,4 +283,46 @@ $toolsdir/iterate ca3 entry3 NEED_KEYINFO,READING_KEYINFO,HAVE_KEYINFO $toolsdir/iterate ca3 entry3 NEED_CSR,GENERATING_CSR $toolsdir/iterate ca3 entry3 NEED_TO_SUBMIT,SUBMITTING $toolsdir/iterate ca3 entry3 "" + +for interval in 0 30 1800 3600 7200 86000 86500 604800 1000000 ; do + for ca in ca-unreachable ca-ask-again ca-unconfigured ; do + echo + echo '[CA poll timeout remaining='$interval'.]' + now=`date +%s` + when=`expr $now + $interval` + then=`env TZ=UTC date -d @$when +%Y%m%d%H%M%S` + cat > entry4 <<- EOF + id=Test + ca_name=Lostie + state=HAVE_CSR + cert_not_after=$then + csr=AAAA + EOF + cat > ca4 <<- EOF + id=Lostie + ca_type=EXTERNAL + ca_external_helper=$tmpdir/$ca + EOF + $toolsdir/iterate ca4 entry4 NEED_TO_SUBMIT,SUBMITTING + done + echo + echo '[Monitor poll timeout remaining='$interval'.]' + now=`date +%s` + when=`expr $now + $interval` + then=`env TZ=UTC date -d @$when +%Y%m%d%H%M%S` + cat > entry4 <<- EOF + id=Test + ca_name=Lostie + state=MONITORING + cert_not_after=$then + csr=AAAA + EOF + cat > ca4 <<- EOF + id=Lostie + ca_type=EXTERNAL + ca_external_helper=$tmpdir/$ca + EOF + $toolsdir/iterate ca4 entry4 "" +done + echo Test complete. diff --git a/tests/tools/iterate.c b/tests/tools/iterate.c index 5c3d225..7d7c691 100644 --- a/tests/tools/iterate.c +++ b/tests/tools/iterate.c @@ -127,6 +127,9 @@ main(int argc, char **argv) } talloc_free(tmp); } + if (when == cm_time_delay) { + printf("delay=%ld\n", (long) delay); + } /* If we didn't find a match, stop here. */ if (*p == '\0') { printf("%s\n-STOP-\n",