From 9972900cb17f0515c38e6bcadda75ec0682fc728 Mon Sep 17 00:00:00 2001 From: David Woodhouse Date: Mon, 17 May 2021 12:26:54 +0100 Subject: [PATCH] Add line length argument to buf_append_base64() The multicert support will want to use this. Signed-off-by: David Woodhouse --- digest.c | 2 +- dtls.c | 2 +- f5.c | 2 +- gssapi.c | 2 +- http-auth.c | 25 ++++++++++++++++++++++--- ntlm.c | 4 ++-- openconnect-internal.h | 2 +- sspi.c | 2 +- 8 files changed, 30 insertions(+), 11 deletions(-) diff --git a/digest.c b/digest.c index 06dca75b..a860ab87 100644 --- a/digest.c +++ b/digest.c @@ -191,7 +191,7 @@ int digest_authorization(struct openconnect_info *vpninfo, int proxy, if (openconnect_random(&cnonce_random, sizeof(cnonce_random))) goto err; cnonce = buf_alloc(); - buf_append_base64(cnonce, cnonce_random, sizeof(cnonce_random)); + buf_append_base64(cnonce, cnonce_random, sizeof(cnonce_random), 0); if (buf_error(cnonce)) goto err; diff --git a/dtls.c b/dtls.c index 1b1c86c2..63df51b9 100644 --- a/dtls.c +++ b/dtls.c @@ -85,7 +85,7 @@ char *openconnect_bin2base64(const char *prefix, const uint8_t *data, unsigned l buf = buf_alloc(); if (prefix) buf_append(buf, "%s", prefix); - buf_append_base64(buf, data, len); + buf_append_base64(buf, data, len, 0); if (!buf_error(buf)) { p = buf->data; diff --git a/f5.c b/f5.c index a6460c6b..df26d2f8 100644 --- a/f5.c +++ b/f5.c @@ -586,7 +586,7 @@ static int f5_configure(struct openconnect_info *vpninfo) buf_truncate(reqbuf); buf_append(reqbuf, "GET /myvpn?sess=%s&hdlc_framing=%s&ipv4=%s&ipv6=%s&Z=%s&hostname=", sid, hdlc?"yes":"no", ipv4?"yes":"no", ipv6?"yes":"no", ur_z); - buf_append_base64(reqbuf, vpninfo->localname, strlen(vpninfo->localname)); + buf_append_base64(reqbuf, vpninfo->localname, strlen(vpninfo->localname), 0); buf_append(reqbuf, " HTTP/1.1\r\n"); struct oc_vpn_option *saved_cookies = vpninfo->cookies; vpninfo->cookies = NULL; /* hide cookies */ diff --git a/gssapi.c b/gssapi.c index 762caea3..6f917149 100644 --- a/gssapi.c +++ b/gssapi.c @@ -135,7 +135,7 @@ int gssapi_authorization(struct openconnect_info *vpninfo, int proxy, return in.value ? -EAGAIN : -ENOENT; } buf_append(hdrbuf, "%sAuthorization: Negotiate ", proxy ? "Proxy-" : ""); - buf_append_base64(hdrbuf, out.value, out.length); + buf_append_base64(hdrbuf, out.value, out.length, 0); buf_append(hdrbuf, "\r\n"); gss_release_buffer(&minor, &out); diff --git a/http-auth.c b/http-auth.c index 7eb89c3d..8c3270b7 100644 --- a/http-auth.c +++ b/http-auth.c @@ -110,7 +110,8 @@ static const char b64_table[] = { 'w', 'x', 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/' }; -void buf_append_base64(struct oc_text_buf *buf, const void *bytes, int len) +void buf_append_base64(struct oc_text_buf *buf, const void *bytes, int len, + int line_len) { const unsigned char *in = bytes; int hibits; @@ -118,10 +119,28 @@ void buf_append_base64(struct oc_text_buf *buf, const void *bytes, int len) if (!buf || buf->error) return; - if (buf_ensure_space(buf, (4 * (len + 2) / 3) + 1)) + unsigned int needed = (4 * (len + 2) / 3) + 1; + if (line_len) + needed += needed / line_len; + + if (needed >= (unsigned)(INT_MAX - buf->pos)) { + buf->error = -E2BIG; + return; + } + + if (buf_ensure_space(buf, needed)) return; + int ll = 0; while (len > 0) { + if (line_len) { + ll += 4; + if (ll >= line_len) { + ll = 0; + buf->data[buf->pos++] = '\n'; + } + } + buf->data[buf->pos++] = b64_table[in[0] >> 2]; hibits = (in[0] << 4) & 0x30; if (len == 1) { @@ -174,7 +193,7 @@ static int basic_authorization(struct openconnect_info *vpninfo, int proxy, return buf_free(text); buf_append(hdrbuf, "%sAuthorization: Basic ", proxy ? "Proxy-" : ""); - buf_append_base64(hdrbuf, text->data, text->pos); + buf_append_base64(hdrbuf, text->data, text->pos, 0); buf_append(hdrbuf, "\r\n"); memset(text->data, 0, text->pos); diff --git a/ntlm.c b/ntlm.c index 61497a50..d7e249c4 100644 --- a/ntlm.c +++ b/ntlm.c @@ -89,7 +89,7 @@ static int ntlm_sspi(struct openconnect_info *vpninfo, int proxy, } buf_append(buf, "%sAuthorization: NTLM ", proxy ? "Proxy-" : ""); - buf_append_base64(buf, out_token.pvBuffer, out_token.cbBuffer); + buf_append_base64(buf, out_token.pvBuffer, out_token.cbBuffer, 0); buf_append(buf, "\r\n"); FreeContextBuffer(out_token.pvBuffer); @@ -971,7 +971,7 @@ static int ntlm_manual_challenge(struct openconnect_info *vpninfo, int proxy, return buf_free(resp); buf_append(hdrbuf, "%sAuthorization: NTLM ", proxy ? "Proxy-" : ""); - buf_append_base64(hdrbuf, resp->data, resp->pos); + buf_append_base64(hdrbuf, resp->data, resp->pos, 0); buf_append(hdrbuf, "\r\n"); buf_free(resp); diff --git a/openconnect-internal.h b/openconnect-internal.h index fb0a580b..754c7159 100644 --- a/openconnect-internal.h +++ b/openconnect-internal.h @@ -1324,7 +1324,7 @@ int handle_redirect(struct openconnect_info *vpninfo); void http_common_headers(struct openconnect_info *vpninfo, struct oc_text_buf *buf); /* http-auth.c */ -void buf_append_base64(struct oc_text_buf *buf, const void *bytes, int len); +void buf_append_base64(struct oc_text_buf *buf, const void *bytes, int len, int line_len); void *openconnect_base64_decode(int *len, const char *in); void clear_auth_states(struct openconnect_info *vpninfo, struct http_auth_state *auth_states, int reset); diff --git a/sspi.c b/sspi.c index 24b2eb19..f0edbb0f 100644 --- a/sspi.c +++ b/sspi.c @@ -120,7 +120,7 @@ int gssapi_authorization(struct openconnect_info *vpninfo, int proxy, } buf_append(hdrbuf, "%sAuthorization: Negotiate ", proxy ? "Proxy-" : ""); - buf_append_base64(hdrbuf, out_token.pvBuffer, out_token.cbBuffer); + buf_append_base64(hdrbuf, out_token.pvBuffer, out_token.cbBuffer, 0); buf_append(hdrbuf, "\r\n"); FreeContextBuffer(out_token.pvBuffer); -- 2.49.0