From: William Lallemand Date: Wed, 9 Apr 2025 15:45:39 +0000 (+0200) Subject: MINOR: acme: handle the nonce X-Git-Tag: v3.2-dev11~96 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=0aa6dedf7253b3153e290088779e7244b7433a14;p=thirdparty%2Fhaproxy.git MINOR: acme: handle the nonce ACME requests are supposed to be sent with a Nonce, the first Nonce should be retrieved using the newNonce URI provided by the directory. This nonce is stored and must be replaced by the new one received in the each response. --- diff --git a/include/haproxy/acme-t.h b/include/haproxy/acme-t.h index db378ff0a..4a0940086 100644 --- a/include/haproxy/acme-t.h +++ b/include/haproxy/acme-t.h @@ -31,6 +31,7 @@ struct acme_cfg { enum acme_st { ACME_RESSOURCES = 0, + ACME_NEWNONCE, ACME_END }; @@ -52,5 +53,6 @@ struct acme_ctx { struct ist newAccount; struct ist newOrder; } ressources; + struct ist nonce; }; #endif diff --git a/src/acme.c b/src/acme.c index cc3ba42de..639932ef2 100644 --- a/src/acme.c +++ b/src/acme.c @@ -529,6 +529,43 @@ error: } +int acme_nonce(struct task *task, struct acme_ctx *ctx, char **errmsg) +{ + struct httpclient *hc; + struct http_hdr *hdrs, *hdr; + + hc = ctx->hc; + if (!hc) + goto error; + + if (hc->res.status < 200 || hc->res.status >= 300) { + memprintf(errmsg, "invalid HTTP status code %d when getting Nonce URL", hc->res.status); + goto error; + } + + hdrs = hc->res.hdrs; + + for (hdr = hdrs; isttest(hdr->v); hdr++) { + if (isteqi(hdr->n, ist("Replay-Nonce"))) { + istfree(&ctx->nonce); + ctx->nonce = istdup(hdr->v); +// fprintf(stderr, "Replay-Nonce: %.*s\n", (int)hdr->v.len, hdr->v.ptr); + + } + } + + httpclient_destroy(hc); + ctx->hc = NULL; + + return 0; + +error: + httpclient_destroy(hc); + ctx->hc = NULL; + + return 1; +} + int acme_directory(struct task *task, struct acme_ctx *ctx, char **errmsg) { struct httpclient *hc; @@ -617,10 +654,25 @@ struct task *acme_process(struct task *task, void *context, unsigned int state) http_st = ACME_HTTP_REQ; goto retry; } - st = ACME_END; + st = ACME_NEWNONCE; + http_st = ACME_HTTP_REQ; + task_wakeup(task, TASK_WOKEN_MSG); } break; + case ACME_NEWNONCE: + if (http_st == ACME_HTTP_REQ) { + if (acme_http_req(task, ctx, ctx->ressources.newNonce, HTTP_METH_HEAD) != 0) + goto retry; + } + if (http_st == ACME_HTTP_RES) { + if (acme_nonce(task, ctx, &errmsg) != 0) { + http_st = ACME_HTTP_REQ; + goto retry; + } + st = ACME_END; + } + break; case ACME_END: goto end; break;