Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion CREDITS
Original file line number Diff line number Diff line change
Expand Up @@ -504,7 +504,7 @@ include/base64.h:
lib/base64.c:

/*
Copyright (C) 2002 Niels Möller, Dan Egnor
Copyright (C) 2002 Niels Möller

This file is part of GNU Nettle.

Expand Down
21 changes: 11 additions & 10 deletions include/base64.h
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
#if HAVE_NETTLE_BASE64_H
#include <nettle/base64.h>

#else /* Base64 functions copied from Nettle 3.4 under GPLv2, with adjustments */
#else /* Base64 functions copied from Nettle 4.0 under GPLv2, with adjustments */

/* base64.h

Expand Down Expand Up @@ -51,6 +51,9 @@
extern "C" {
#endif

#define BASE64_BINARY_BLOCK_SIZE 3
#define BASE64_TEXT_BLOCK_SIZE 4

/* Base64 encoding */

/* Maximum length of output for base64_encode_update. NOTE: Doesn't
Expand Down Expand Up @@ -104,15 +107,12 @@ base64_encode_final(struct base64_encode_ctx *ctx,

/* Encodes a string in one go, including any padding at the end.
* Generates exactly BASE64_ENCODE_RAW_LENGTH(length) bytes of output.
* Supports overlapped operation, if src <= dst.
* TODO: Use of overlap is deprecated, if needed there should be a separate public function
* Supports overlapped operation, if src <= dst. FIXME: Use of overlap
* is deprecated, if needed there should be a separate public function
* to do that.*/
void
base64_encode_raw(char *dst, size_t length, const uint8_t *src);

void
base64_encode_group(char *dst, uint32_t group);

/* Base64 decoding */

/* Maximum length of output for base64_decode_update. */
Expand Down Expand Up @@ -145,8 +145,10 @@ base64_decode_single(struct base64_decode_ctx *ctx,
char src);

/* Returns 1 on success, 0 on error. DST should point to an area of
* size at least BASE64_DECODE_LENGTH(length). The amount of data
* generated is returned in *DST_LENGTH. */
* size *DST_LENGTH. Decoding returns failure it output would exceed
* this size. BASE64_DECODE_LENGTH(length) is always sufficient.
* *DST_LENGTH is updated to reflect the amount of data actually
* generated. */
int
base64_decode_update(struct base64_decode_ctx *ctx,
size_t *dst_length,
Expand All @@ -165,8 +167,7 @@ base64_decode_final(struct base64_decode_ctx *ctx);
#endif /* HAVE_NETTLE_BASE64_H */

/// Calculate the buffer size required to hold the encoded form of
/// a string of length 'decodedLen' including all terminator bytes.
/// a string of length bytes, including all terminator bytes.
#define base64_encode_len(length) (BASE64_ENCODE_LENGTH(length)+BASE64_ENCODE_FINAL_LENGTH+1)

#endif /* SQUID_INCLUDE_BASE64_H */

106 changes: 42 additions & 64 deletions lib/base64.c
Original file line number Diff line number Diff line change
Expand Up @@ -7,16 +7,15 @@
*/

/*
* Copied from Nettle 3.4 under GPLv2, with adjustments
* Copied from Nettle 4.0 under GPLv2, with adjustments
*/

#include "squid.h"
#include "base64.h"

#if !HAVE_NETTLE_BASE64_H

/* base64-encode.c

/*
Copyright (C) 2002 Niels Möller

This file is part of GNU Nettle.
Expand Down Expand Up @@ -46,6 +45,8 @@
not, see http://www.gnu.org/licenses/.
*/

/* base64-decode.c */

#define TABLE_INVALID -1
#define TABLE_SPACE -2
#define TABLE_END -3
Expand Down Expand Up @@ -83,46 +84,9 @@ base64_decode_single(struct base64_decode_ctx *ctx,
uint8_t *dst,
char src)
{
int data = ctx->table[(uint8_t) src];

switch(data)
{
default:
assert(data >= 0 && data < 0x40);

if (ctx->padding)
return -1;

ctx->word = ctx->word << 6 | data;
ctx->bits += 6;

if (ctx->bits >= 8)
{
ctx->bits -= 8;
dst[0] = ctx->word >> ctx->bits;
return 1;
}
else return 0;

case TABLE_INVALID:
return -1;

case TABLE_SPACE:
return 0;

case TABLE_END:
/* There can be at most two padding characters. */
if (!ctx->bits || ctx->padding > 2)
return -1;

if (ctx->word & ( (1<<ctx->bits) - 1))
/* We shouldn't have any leftover bits */
return -1;

ctx->padding++;
ctx->bits -= 2;
return 0;
}
size_t dst_length = 1;
return base64_decode_update (ctx, &dst_length, dst, 1, &src)
? dst_length : -1;
}

int
Expand All @@ -135,20 +99,44 @@ base64_decode_update(struct base64_decode_ctx *ctx,
size_t done;
size_t i;

for (i = 0, done = 0; i<src_length; i++)
switch(base64_decode_single(ctx, dst + done, src[i]))
for (i = done = 0; i<src_length; i++)
{
int data = ctx->table[(uint8_t) src[i]];
switch (data)
{
case -1:
return 0;
case 1:
done++;
/* Fall through */
case 0:
break;
default:
abort();
}
assert(data >= 0 && data < 0x40);

if (ctx->padding || (done >= *dst_length))
return -1;

ctx->word = ctx->word << 6 | data;
ctx->bits += 6;

if (ctx->bits >= 8)
{
ctx->bits -= 8;
dst[done++] = ctx->word >> ctx->bits;
}
break;
case TABLE_INVALID:
return -1;
case TABLE_SPACE:
continue;
case TABLE_END:
/* There can be at most two padding characters. */
if (!ctx->bits || ctx->padding > 2)
return -1;

if (ctx->word & ( (1<<ctx->bits) - 1))
/* We shouldn't have any leftover bits */
return -1;

ctx->padding++;
ctx->bits -= 2;
break;
}
}
assert(done <= BASE64_DECODE_LENGTH(src_length));

*dst_length = done;
Expand Down Expand Up @@ -219,15 +207,6 @@ base64_encode_raw(char *dst, size_t length, const uint8_t *src)
encode_raw(base64_encode_table, dst, length, src);
}

void
base64_encode_group(char *dst, uint32_t group)
{
*dst++ = ENCODE(base64_encode_table, (group >> 18));
*dst++ = ENCODE(base64_encode_table, (group >> 12));
*dst++ = ENCODE(base64_encode_table, (group >> 6));
*dst++ = ENCODE(base64_encode_table, group);
}

void
base64_encode_init(struct base64_encode_ctx *ctx)
{
Expand Down Expand Up @@ -325,4 +304,3 @@ base64_encode_final(struct base64_encode_ctx *ctx,
}

#endif /* !HAVE_NETTLE_BASE64_H */

4 changes: 2 additions & 2 deletions src/HttpHeader.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1434,10 +1434,10 @@ HttpHeader::getAuthToken(Http::HdrType id, const char *auth_scheme) const

const auto fieldLen = strlen(field);
SBuf result;
char *decodedAuthToken = result.rawAppendStart(BASE64_DECODE_LENGTH(fieldLen));
struct base64_decode_ctx ctx;
base64_decode_init(&ctx);
size_t decodedLen = 0;
size_t decodedLen = BASE64_DECODE_LENGTH(fieldLen);
char *decodedAuthToken = result.rawAppendStart(decodedLen);
if (!base64_decode_update(&ctx, &decodedLen, reinterpret_cast<uint8_t*>(decodedAuthToken), fieldLen, field) ||
!base64_decode_final(&ctx)) {
return nil;
Expand Down
2 changes: 1 addition & 1 deletion src/auth/basic/Config.cc
Original file line number Diff line number Diff line change
Expand Up @@ -170,7 +170,7 @@ Auth::Basic::Config::decodeCleartext(const char *httpAuthHeader, const HttpReque
struct base64_decode_ctx ctx;
base64_decode_init(&ctx);

size_t dstLen = 0;
size_t dstLen = sizeof(cleartext);
if (base64_decode_update(&ctx, &dstLen, reinterpret_cast<uint8_t*>(cleartext), srcLen, eek) && base64_decode_final(&ctx)) {
cleartext[dstLen] = '\0';

Expand Down
2 changes: 2 additions & 0 deletions src/auth/negotiate/SSPI/negotiate_sspi_auth.cc
Original file line number Diff line number Diff line change
Expand Up @@ -124,10 +124,12 @@ token_decode(size_t *decodedLen, uint8_t decoded[], const char *buf)
{
struct base64_decode_ctx ctx;
base64_decode_init(&ctx);
decodedLen = sizeof(decoded);
if (!base64_decode_update(&ctx, decodedLen, decoded, strlen(buf), buf) ||
!base64_decode_final(&ctx)) {
SEND("BH base64 decode failed");
fprintf(stderr, "ERROR: base64 decoding failed for: '%s'\n", buf);
decodedLen = 0;
return false;
}
return true;
Expand Down
2 changes: 1 addition & 1 deletion src/auth/negotiate/kerberos/negotiate_kerberos_auth.cc
Original file line number Diff line number Diff line change
Expand Up @@ -658,7 +658,7 @@ main(int argc, char *const argv[])

struct base64_decode_ctx ctx;
base64_decode_init(&ctx);
size_t dstLen = 0;
size_t dstLen = sizeof(input_token.value);
if (!base64_decode_update(&ctx, &dstLen, static_cast<uint8_t*>(input_token.value), srcLen, b64Token) ||
!base64_decode_final(&ctx)) {
debug((char *) "%s| %s: ERROR: Invalid base64 token [%s]\n", LogTime(), PROGRAM, b64Token);
Expand Down
2 changes: 1 addition & 1 deletion src/auth/negotiate/wrapper/negotiate_wrapper.cc
Original file line number Diff line number Diff line change
Expand Up @@ -189,7 +189,7 @@ processingLoop(FILE *FDKIN, FILE *FDKOUT, FILE *FDNIN, FILE *FDNOUT)

struct base64_decode_ctx ctx;
base64_decode_init(&ctx);
size_t dstLen = 0;
size_t dstLen = sizeof(token);
if (!base64_decode_update(&ctx, &dstLen, token, strlen(buf+3), buf+3) ||
!base64_decode_final(&ctx)) {
if (debug_enabled)
Expand Down
2 changes: 1 addition & 1 deletion src/auth/ntlm/fake/ntlm_fake_auth.cc
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ main(int argc, char *argv[])
ntlmhdr *packet;
struct base64_decode_ctx ctx;
base64_decode_init(&ctx);
size_t dstLen = 0;
size_t dstLen = sizeof(decodedBuf);
if (buflen > 3 &&
base64_decode_update(&ctx, &dstLen, decodedBuf, buflen-3, buf+3) &&
base64_decode_final(&ctx)) {
Expand Down
Loading