Early last year (2023) not-a-blog was extolling the versatility of wuCME
https://wasd.vsm.com.au/info-WASD/2023/0035
then another, Oversize Tools -- A Cautionary Tale, also featured wuCME
https://wasd.vsm.com.au/info-WASD/2024/0003
And recently an info-WASD email announcing an update to v1.1.9 and urging
those using it to upgrade as soon as possible. No, not a security issue.
More a bite-in-the-bum issue. In the second of the above is this insight
"wuCME -- and this is significant -- is based on a GPL licensed code
base, written in plain C, and "wrapped" with some more C code for use
with WASD. So I didn't write the algorithms employed nor really come
to grips with the internals. Thank you Nicola Di Lieto. It just worked."
concluding, somewhat ominously,
"Until recently."
Now the "nor really come to grips with the internals", has returned like the
Ghost of Christmas Past.
The wuCME version log begins
01-JUN-2020 MGD v1.0.0, initial release
08-AUG-2019 MGD initial development
so just over four years in production. Four years, and hundreds of Let's
Encrypt certificates issued across multiple systems (with a few enhancements
and tweaks along the way) ... basically all due to serendipity.
Within a handful of days some fifty months on, multiple reports emerged of
strange challenge꙳꙳ failures. In particular
challenge=tls-alpn-01 ident=www.******.au token=bxf_******aPg8 key_auth=ZYPv******EMxBc
and also the likes of
challenge=dns-01 ident=www.******.au token=oMj3Vk******A3VU key_auth=cayvE2 ******QbAuY
but challenges that were successful as well
challenge=http-01 ident=www.******.au token=bxf******jbaPg8 key_auth=bxf_y******d9_G-L8
I had coded wuCME's use of the core uacme.c on the presumption that unless
you specified an alternate, the challenge defaulted to the simplest,
"http-01". Nope! Incorrect! Not even close! wuCME defaults to the first
*offered* by the Let's Encrypt servers. LE currently offers *three*.
Just happened that for the first four years of wuCME production LE must have
offered "http-01" first, which wuCME supported. Recently LE's algorithm
obviously changed from a fixed order of challenges, to a varying order.
wuCME's simple grab the first and run as often as not was suddenly broken
(probably with a large enough sample, 2 in 3 likely broken :-)
This bug had remained latent for all those years.
The fix, an embarrassing
if (strcmp (type, "http-01"))
{
/* discard unsupported challenge */
free(key_auth);
continue;
}
And to rub salt into the wound, the uacme.c default behaviour (right *there*
in adjacent code) is to similarly step through the challenges allowing the
user to accept or decline each provided by LE.
msg(0, "type 'y' followed by a newline to accept challenge"
", anything else to skip");
if (scanf(" %c", &c) != 1 || tolower(c) != 'y') {
free(key_auth);
continue;
}
Thanks to the LE community for their inputs.
꙳꙳ https://letsencrypt.org/docs/challenge-types/
This item is one of a collection at
https://wasd.vsm.com.au/other/#occasional
|