/*
 * Copyright (c) 2004 - 2022 Marcus Glocker <marcus@nazgul.ch>
 *
 * Permission to use, copy, modify, and distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

#include <string.h>

/* data */

static const unsigned char encode[64] =
	"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";

/*
 * base64e()
 * 	reads plain text from src and encodes it to base64 in dst
 * Return:
 *	0 = success, -1 = failed
 */

int
strb64e(char *dst, const char *src, const int dsize)
{
	int             i, j, k;
	unsigned char   in_a[3], out[4];

	k = 0;

	for (;;) {
		in_a[0] = in_a[1] = in_a[2] = 0;

		for (i = 0; i < 3; i++) {
			if (*src == '\0')
				break;
			in_a[i] = *src;
			src++;
		}

		/* split the 24-bit field in 4 6-bit */
		out[0] = encode[(in_a[0] >> 2)];
		out[1] = encode[((in_a[0] & 3) << 4) | (in_a[1] >> 4)];
		out[2] = i < 2 ? '=' : encode[((in_a[1] & 15) << 2) |
		    (in_a[2] >> 6)];
		out[3] = i < 3 ? '=' : encode[(in_a[2] & 63)];

		/* fill up buffer */
		for (j = 0; j < 4; j++) {
			if (k >= dsize)
				return -1;
			dst[k] = out[j];
			k++;
		}

		/* finished */
		if (i != 3)
			break;
	}
	if (k >= dsize)
		return -1;
	dst[k] = '\0';

	return 0;
}
