xref: /openbsd-src/lib/libcrypto/evp/evp_encode.c (revision 9bac3682a248384cde711fdda825c3b5960b1005)
1*9bac3682Sbeck /* $OpenBSD: evp_encode.c,v 1.3 2024/04/09 13:52:41 beck Exp $ */
21cc76114Stb /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
31cc76114Stb  * All rights reserved.
41cc76114Stb  *
51cc76114Stb  * This package is an SSL implementation written
61cc76114Stb  * by Eric Young (eay@cryptsoft.com).
71cc76114Stb  * The implementation was written so as to conform with Netscapes SSL.
81cc76114Stb  *
91cc76114Stb  * This library is free for commercial and non-commercial use as long as
101cc76114Stb  * the following conditions are aheared to.  The following conditions
111cc76114Stb  * apply to all code found in this distribution, be it the RC4, RSA,
121cc76114Stb  * lhash, DES, etc., code; not just the SSL code.  The SSL documentation
131cc76114Stb  * included with this distribution is covered by the same copyright terms
141cc76114Stb  * except that the holder is Tim Hudson (tjh@cryptsoft.com).
151cc76114Stb  *
161cc76114Stb  * Copyright remains Eric Young's, and as such any Copyright notices in
171cc76114Stb  * the code are not to be removed.
181cc76114Stb  * If this package is used in a product, Eric Young should be given attribution
191cc76114Stb  * as the author of the parts of the library used.
201cc76114Stb  * This can be in the form of a textual message at program startup or
211cc76114Stb  * in documentation (online or textual) provided with the package.
221cc76114Stb  *
231cc76114Stb  * Redistribution and use in source and binary forms, with or without
241cc76114Stb  * modification, are permitted provided that the following conditions
251cc76114Stb  * are met:
261cc76114Stb  * 1. Redistributions of source code must retain the copyright
271cc76114Stb  *    notice, this list of conditions and the following disclaimer.
281cc76114Stb  * 2. Redistributions in binary form must reproduce the above copyright
291cc76114Stb  *    notice, this list of conditions and the following disclaimer in the
301cc76114Stb  *    documentation and/or other materials provided with the distribution.
311cc76114Stb  * 3. All advertising materials mentioning features or use of this software
321cc76114Stb  *    must display the following acknowledgement:
331cc76114Stb  *    "This product includes cryptographic software written by
341cc76114Stb  *     Eric Young (eay@cryptsoft.com)"
351cc76114Stb  *    The word 'cryptographic' can be left out if the rouines from the library
361cc76114Stb  *    being used are not cryptographic related :-).
371cc76114Stb  * 4. If you include any Windows specific code (or a derivative thereof) from
381cc76114Stb  *    the apps directory (application code) you must include an acknowledgement:
391cc76114Stb  *    "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
401cc76114Stb  *
411cc76114Stb  * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
421cc76114Stb  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
431cc76114Stb  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
441cc76114Stb  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
451cc76114Stb  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
461cc76114Stb  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
471cc76114Stb  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
481cc76114Stb  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
491cc76114Stb  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
501cc76114Stb  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
511cc76114Stb  * SUCH DAMAGE.
521cc76114Stb  *
531cc76114Stb  * The licence and distribution terms for any publically available version or
541cc76114Stb  * derivative of this code cannot be changed.  i.e. this code cannot simply be
551cc76114Stb  * copied and put under another distribution licence
561cc76114Stb  * [including the GNU Public Licence.]
571cc76114Stb  */
581cc76114Stb 
591cc76114Stb #include <limits.h>
601cc76114Stb #include <stdio.h>
611cc76114Stb #include <string.h>
621cc76114Stb 
631cc76114Stb #include <openssl/evp.h>
641cc76114Stb 
651cc76114Stb #include "evp_local.h"
661cc76114Stb 
671cc76114Stb static unsigned char conv_ascii2bin(unsigned char a);
681cc76114Stb #define conv_bin2ascii(a)	(data_bin2ascii[(a)&0x3f])
691cc76114Stb 
701cc76114Stb /* 64 char lines
711cc76114Stb  * pad input with 0
721cc76114Stb  * left over chars are set to =
731cc76114Stb  * 1 byte  => xx==
741cc76114Stb  * 2 bytes => xxx=
751cc76114Stb  * 3 bytes => xxxx
761cc76114Stb  */
771cc76114Stb #define BIN_PER_LINE    (64/4*3)
781cc76114Stb #define CHUNKS_PER_LINE (64/4)
791cc76114Stb #define CHAR_PER_LINE   (64+1)
801cc76114Stb 
811cc76114Stb static const unsigned char data_bin2ascii[65] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ\
821cc76114Stb abcdefghijklmnopqrstuvwxyz0123456789+/";
831cc76114Stb 
841cc76114Stb /* 0xF0 is a EOLN
851cc76114Stb  * 0xF1 is ignore but next needs to be 0xF0 (for \r\n processing).
861cc76114Stb  * 0xF2 is EOF
871cc76114Stb  * 0xE0 is ignore at start of line.
881cc76114Stb  * 0xFF is error
891cc76114Stb  */
901cc76114Stb 
911cc76114Stb #define B64_EOLN		0xF0
921cc76114Stb #define B64_CR			0xF1
931cc76114Stb #define B64_EOF			0xF2
941cc76114Stb #define B64_WS			0xE0
951cc76114Stb #define B64_ERROR		0xFF
961cc76114Stb #define B64_NOT_BASE64(a)	(((a)|0x13) == 0xF3)
971cc76114Stb #define B64_BASE64(a)		!B64_NOT_BASE64(a)
981cc76114Stb 
991cc76114Stb static const unsigned char data_ascii2bin[128] = {
1001cc76114Stb 	0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
1011cc76114Stb 	0xFF, 0xE0, 0xF0, 0xFF, 0xFF, 0xF1, 0xFF, 0xFF,
1021cc76114Stb 	0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
1031cc76114Stb 	0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
1041cc76114Stb 	0xE0, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
1051cc76114Stb 	0xFF, 0xFF, 0xFF, 0x3E, 0xFF, 0xF2, 0xFF, 0x3F,
1061cc76114Stb 	0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x3B,
1071cc76114Stb 	0x3C, 0x3D, 0xFF, 0xFF, 0xFF, 0x00, 0xFF, 0xFF,
1081cc76114Stb 	0xFF, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06,
1091cc76114Stb 	0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E,
1101cc76114Stb 	0x0F, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16,
1111cc76114Stb 	0x17, 0x18, 0x19, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
1121cc76114Stb 	0xFF, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, 0x20,
1131cc76114Stb 	0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28,
1141cc76114Stb 	0x29, 0x2A, 0x2B, 0x2C, 0x2D, 0x2E, 0x2F, 0x30,
1151cc76114Stb 	0x31, 0x32, 0x33, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
1161cc76114Stb };
1171cc76114Stb 
1181cc76114Stb static unsigned char
conv_ascii2bin(unsigned char a)1191cc76114Stb conv_ascii2bin(unsigned char a)
1201cc76114Stb {
1211cc76114Stb 	if (a & 0x80)
1221cc76114Stb 		return B64_ERROR;
1231cc76114Stb 	return data_ascii2bin[a];
1241cc76114Stb }
1251cc76114Stb 
1261cc76114Stb EVP_ENCODE_CTX *
EVP_ENCODE_CTX_new(void)1271cc76114Stb EVP_ENCODE_CTX_new(void)
1281cc76114Stb {
1291cc76114Stb 	return calloc(1, sizeof(EVP_ENCODE_CTX));
1301cc76114Stb }
131*9bac3682Sbeck LCRYPTO_ALIAS(EVP_ENCODE_CTX_new);
1321cc76114Stb 
1331cc76114Stb void
EVP_ENCODE_CTX_free(EVP_ENCODE_CTX * ctx)1341cc76114Stb EVP_ENCODE_CTX_free(EVP_ENCODE_CTX *ctx)
1351cc76114Stb {
1361cc76114Stb 	free(ctx);
1371cc76114Stb }
138*9bac3682Sbeck LCRYPTO_ALIAS(EVP_ENCODE_CTX_free);
1391cc76114Stb 
1401cc76114Stb void
EVP_EncodeInit(EVP_ENCODE_CTX * ctx)1411cc76114Stb EVP_EncodeInit(EVP_ENCODE_CTX *ctx)
1421cc76114Stb {
1431cc76114Stb 	ctx->length = 48;
1441cc76114Stb 	ctx->num = 0;
1451cc76114Stb 	ctx->line_num = 0;
1461cc76114Stb }
147*9bac3682Sbeck LCRYPTO_ALIAS(EVP_EncodeInit);
1481cc76114Stb 
1491cc76114Stb int
EVP_EncodeUpdate(EVP_ENCODE_CTX * ctx,unsigned char * out,int * outl,const unsigned char * in,int inl)1501cc76114Stb EVP_EncodeUpdate(EVP_ENCODE_CTX *ctx, unsigned char *out, int *outl,
1511cc76114Stb     const unsigned char *in, int inl)
1521cc76114Stb {
1531cc76114Stb 	int i, j;
1541cc76114Stb 	size_t total = 0;
1551cc76114Stb 
1561cc76114Stb 	*outl = 0;
1571cc76114Stb 	if (inl <= 0)
1581cc76114Stb 		return 0;
1591cc76114Stb 	OPENSSL_assert(ctx->length <= (int)sizeof(ctx->enc_data));
1601cc76114Stb 	if (ctx->length - ctx->num > inl) {
1611cc76114Stb 		memcpy(&(ctx->enc_data[ctx->num]), in, inl);
1621cc76114Stb 		ctx->num += inl;
1631cc76114Stb 		return 1;
1641cc76114Stb 	}
1651cc76114Stb 	if (ctx->num != 0) {
1661cc76114Stb 		i = ctx->length - ctx->num;
1671cc76114Stb 		memcpy(&(ctx->enc_data[ctx->num]), in, i);
1681cc76114Stb 		in += i;
1691cc76114Stb 		inl -= i;
1701cc76114Stb 		j = EVP_EncodeBlock(out, ctx->enc_data, ctx->length);
1711cc76114Stb 		ctx->num = 0;
1721cc76114Stb 		out += j;
1731cc76114Stb 		*(out++) = '\n';
1741cc76114Stb 		*out = '\0';
1751cc76114Stb 		total = j + 1;
1761cc76114Stb 	}
1771cc76114Stb 	while (inl >= ctx->length && total <= INT_MAX) {
1781cc76114Stb 		j = EVP_EncodeBlock(out, in, ctx->length);
1791cc76114Stb 		in += ctx->length;
1801cc76114Stb 		inl -= ctx->length;
1811cc76114Stb 		out += j;
1821cc76114Stb 		*(out++) = '\n';
1831cc76114Stb 		*out = '\0';
1841cc76114Stb 		total += j + 1;
1851cc76114Stb 	}
1861cc76114Stb 	if (total > INT_MAX) {
1871cc76114Stb 		/* Too much output data! */
1881cc76114Stb 		*outl = 0;
1891cc76114Stb 		return 0;
1901cc76114Stb 	}
1911cc76114Stb 	if (inl != 0)
1921cc76114Stb 		memcpy(&(ctx->enc_data[0]), in, inl);
1931cc76114Stb 	ctx->num = inl;
1941cc76114Stb 	*outl = total;
1951cc76114Stb 
1961cc76114Stb 	return 1;
1971cc76114Stb }
198*9bac3682Sbeck LCRYPTO_ALIAS(EVP_EncodeUpdate);
1991cc76114Stb 
2001cc76114Stb void
EVP_EncodeFinal(EVP_ENCODE_CTX * ctx,unsigned char * out,int * outl)2011cc76114Stb EVP_EncodeFinal(EVP_ENCODE_CTX *ctx, unsigned char *out, int *outl)
2021cc76114Stb {
2031cc76114Stb 	unsigned int ret = 0;
2041cc76114Stb 
2051cc76114Stb 	if (ctx->num != 0) {
2061cc76114Stb 		ret = EVP_EncodeBlock(out, ctx->enc_data, ctx->num);
2071cc76114Stb 		out[ret++] = '\n';
2081cc76114Stb 		out[ret] = '\0';
2091cc76114Stb 		ctx->num = 0;
2101cc76114Stb 	}
2111cc76114Stb 	*outl = ret;
2121cc76114Stb }
213*9bac3682Sbeck LCRYPTO_ALIAS(EVP_EncodeFinal);
2141cc76114Stb 
2151cc76114Stb int
EVP_EncodeBlock(unsigned char * t,const unsigned char * f,int dlen)2161cc76114Stb EVP_EncodeBlock(unsigned char *t, const unsigned char *f, int dlen)
2171cc76114Stb {
2181cc76114Stb 	int i, ret = 0;
2191cc76114Stb 	unsigned long l;
2201cc76114Stb 
2211cc76114Stb 	for (i = dlen; i > 0; i -= 3) {
2221cc76114Stb 		if (i >= 3) {
2231cc76114Stb 			l = (((unsigned long)f[0]) << 16L) |
2241cc76114Stb 			    (((unsigned long)f[1]) << 8L) | f[2];
2251cc76114Stb 			*(t++) = conv_bin2ascii(l >> 18L);
2261cc76114Stb 			*(t++) = conv_bin2ascii(l >> 12L);
2271cc76114Stb 			*(t++) = conv_bin2ascii(l >> 6L);
2281cc76114Stb 			*(t++) = conv_bin2ascii(l     );
2291cc76114Stb 		} else {
2301cc76114Stb 			l = ((unsigned long)f[0]) << 16L;
2311cc76114Stb 			if (i == 2)
2321cc76114Stb 				l |= ((unsigned long)f[1] << 8L);
2331cc76114Stb 
2341cc76114Stb 			*(t++) = conv_bin2ascii(l >> 18L);
2351cc76114Stb 			*(t++) = conv_bin2ascii(l >> 12L);
2361cc76114Stb 			*(t++) = (i == 1) ? '=' : conv_bin2ascii(l >> 6L);
2371cc76114Stb 			*(t++) = '=';
2381cc76114Stb 		}
2391cc76114Stb 		ret += 4;
2401cc76114Stb 		f += 3;
2411cc76114Stb 	}
2421cc76114Stb 
2431cc76114Stb 	*t = '\0';
2441cc76114Stb 	return (ret);
2451cc76114Stb }
246*9bac3682Sbeck LCRYPTO_ALIAS(EVP_EncodeBlock);
2471cc76114Stb 
2481cc76114Stb void
EVP_DecodeInit(EVP_ENCODE_CTX * ctx)2491cc76114Stb EVP_DecodeInit(EVP_ENCODE_CTX *ctx)
2501cc76114Stb {
2511cc76114Stb 	ctx->num = 0;
2521cc76114Stb 	ctx->length = 0;
2531cc76114Stb 	ctx->line_num = 0;
2541cc76114Stb 	ctx->expect_nl = 0;
2551cc76114Stb }
256*9bac3682Sbeck LCRYPTO_ALIAS(EVP_DecodeInit);
2571cc76114Stb 
2581cc76114Stb int
EVP_DecodeUpdate(EVP_ENCODE_CTX * ctx,unsigned char * out,int * outl,const unsigned char * in,int inl)2591cc76114Stb EVP_DecodeUpdate(EVP_ENCODE_CTX *ctx, unsigned char *out, int *outl,
2601cc76114Stb     const unsigned char *in, int inl)
2611cc76114Stb {
2621cc76114Stb 	int seof = 0, eof = 0, rv = -1, ret = 0, i, v, tmp, n, decoded_len;
2631cc76114Stb 	unsigned char *d;
2641cc76114Stb 
2651cc76114Stb 	n = ctx->num;
2661cc76114Stb 	d = ctx->enc_data;
2671cc76114Stb 
2681cc76114Stb 	if (n > 0 && d[n - 1] == '=') {
2691cc76114Stb 		eof++;
2701cc76114Stb 		if (n > 1 && d[n - 2] == '=')
2711cc76114Stb 			eof++;
2721cc76114Stb 	}
2731cc76114Stb 
2741cc76114Stb 	/* Legacy behaviour: an empty input chunk signals end of input. */
2751cc76114Stb 	if (inl == 0) {
2761cc76114Stb 		rv = 0;
2771cc76114Stb 		goto end;
2781cc76114Stb 	}
2791cc76114Stb 
2801cc76114Stb 	for (i = 0; i < inl; i++) {
2811cc76114Stb 		tmp = *(in++);
2821cc76114Stb 		v = conv_ascii2bin(tmp);
2831cc76114Stb 		if (v == B64_ERROR) {
2841cc76114Stb 			rv = -1;
2851cc76114Stb 			goto end;
2861cc76114Stb 		}
2871cc76114Stb 
2881cc76114Stb 		if (tmp == '=') {
2891cc76114Stb 			eof++;
2901cc76114Stb 		} else if (eof > 0 && B64_BASE64(v)) {
2911cc76114Stb 			/* More data after padding. */
2921cc76114Stb 			rv = -1;
2931cc76114Stb 			goto end;
2941cc76114Stb 		}
2951cc76114Stb 
2961cc76114Stb 		if (eof > 2) {
2971cc76114Stb 			rv = -1;
2981cc76114Stb 			goto end;
2991cc76114Stb 		}
3001cc76114Stb 
3011cc76114Stb 		if (v == B64_EOF) {
3021cc76114Stb 			seof = 1;
3031cc76114Stb 			goto tail;
3041cc76114Stb 		}
3051cc76114Stb 
3061cc76114Stb 		/* Only save valid base64 characters. */
3071cc76114Stb 		if (B64_BASE64(v)) {
3081cc76114Stb 			if (n >= 64) {
3091cc76114Stb 				/*
3101cc76114Stb 				 * We increment n once per loop, and empty the
3111cc76114Stb 				 * buffer as soon as we reach 64 characters, so
3121cc76114Stb 				 * this can only happen if someone's manually
3131cc76114Stb 				 * messed with the ctx. Refuse to write any
3141cc76114Stb 				 * more data.
3151cc76114Stb 				 */
3161cc76114Stb 				rv = -1;
3171cc76114Stb 				goto end;
3181cc76114Stb 			}
3191cc76114Stb 			OPENSSL_assert(n < (int)sizeof(ctx->enc_data));
3201cc76114Stb 			d[n++] = tmp;
3211cc76114Stb 		}
3221cc76114Stb 
3231cc76114Stb 		if (n == 64) {
3241cc76114Stb 			decoded_len = EVP_DecodeBlock(out, d, n);
3251cc76114Stb 			n = 0;
3261cc76114Stb 			if (decoded_len < 0 || eof > decoded_len) {
3271cc76114Stb 				rv = -1;
3281cc76114Stb 				goto end;
3291cc76114Stb 			}
3301cc76114Stb 			ret += decoded_len - eof;
3311cc76114Stb 			out += decoded_len - eof;
3321cc76114Stb 		}
3331cc76114Stb 	}
3341cc76114Stb 
3351cc76114Stb 	/*
3361cc76114Stb 	 * Legacy behaviour: if the current line is a full base64-block (i.e.,
3371cc76114Stb 	 * has 0 mod 4 base64 characters), it is processed immediately. We keep
3381cc76114Stb 	 * this behaviour as applications may not be calling EVP_DecodeFinal
3391cc76114Stb 	 * properly.
3401cc76114Stb 	 */
3411cc76114Stb  tail:
3421cc76114Stb 	if (n > 0) {
3431cc76114Stb 		if ((n & 3) == 0) {
3441cc76114Stb 			decoded_len = EVP_DecodeBlock(out, d, n);
3451cc76114Stb 			n = 0;
3461cc76114Stb 			if (decoded_len < 0 || eof > decoded_len) {
3471cc76114Stb 				rv = -1;
3481cc76114Stb 				goto end;
3491cc76114Stb 			}
3501cc76114Stb 			ret += (decoded_len - eof);
3511cc76114Stb 		} else if (seof) {
3521cc76114Stb 			/* EOF in the middle of a base64 block. */
3531cc76114Stb 			rv = -1;
3541cc76114Stb 			goto end;
3551cc76114Stb 		}
3561cc76114Stb 	}
3571cc76114Stb 
3581cc76114Stb 	rv = seof || (n == 0 && eof) ? 0 : 1;
3591cc76114Stb  end:
3601cc76114Stb 	/* Legacy behaviour. This should probably rather be zeroed on error. */
3611cc76114Stb 	*outl = ret;
3621cc76114Stb 	ctx->num = n;
3631cc76114Stb 	return (rv);
3641cc76114Stb }
365*9bac3682Sbeck LCRYPTO_ALIAS(EVP_DecodeUpdate);
3661cc76114Stb 
3671cc76114Stb int
EVP_DecodeBlock(unsigned char * t,const unsigned char * f,int n)3681cc76114Stb EVP_DecodeBlock(unsigned char *t, const unsigned char *f, int n)
3691cc76114Stb {
3701cc76114Stb 	int i, ret = 0, a, b, c, d;
3711cc76114Stb 	unsigned long l;
3721cc76114Stb 
3731cc76114Stb 	/* trim white space from the start of the line. */
3741cc76114Stb 	while ((conv_ascii2bin(*f) == B64_WS) && (n > 0)) {
3751cc76114Stb 		f++;
3761cc76114Stb 		n--;
3771cc76114Stb 	}
3781cc76114Stb 
3791cc76114Stb 	/* strip off stuff at the end of the line
3801cc76114Stb 	 * ascii2bin values B64_WS, B64_EOLN, B64_EOLN and B64_EOF */
3811cc76114Stb 	while ((n > 3) && (B64_NOT_BASE64(conv_ascii2bin(f[n - 1]))))
3821cc76114Stb 		n--;
3831cc76114Stb 
3841cc76114Stb 	if (n % 4 != 0)
3851cc76114Stb 		return (-1);
3861cc76114Stb 
3871cc76114Stb 	for (i = 0; i < n; i += 4) {
3881cc76114Stb 		a = conv_ascii2bin(*(f++));
3891cc76114Stb 		b = conv_ascii2bin(*(f++));
3901cc76114Stb 		c = conv_ascii2bin(*(f++));
3911cc76114Stb 		d = conv_ascii2bin(*(f++));
3921cc76114Stb 		if ((a & 0x80) || (b & 0x80) ||
3931cc76114Stb 		    (c & 0x80) || (d & 0x80))
3941cc76114Stb 			return (-1);
3951cc76114Stb 		l = ((((unsigned long)a) << 18L) |
3961cc76114Stb 		    (((unsigned long)b) << 12L) |
3971cc76114Stb 		    (((unsigned long)c) << 6L) |
3981cc76114Stb 		    (((unsigned long)d)));
3991cc76114Stb 		*(t++) = (unsigned char)(l >> 16L) & 0xff;
4001cc76114Stb 		*(t++) = (unsigned char)(l >> 8L) & 0xff;
4011cc76114Stb 		*(t++) = (unsigned char)(l) & 0xff;
4021cc76114Stb 		ret += 3;
4031cc76114Stb 	}
4041cc76114Stb 	return (ret);
4051cc76114Stb }
406*9bac3682Sbeck LCRYPTO_ALIAS(EVP_DecodeBlock);
4071cc76114Stb 
4081cc76114Stb int
EVP_DecodeFinal(EVP_ENCODE_CTX * ctx,unsigned char * out,int * outl)4091cc76114Stb EVP_DecodeFinal(EVP_ENCODE_CTX *ctx, unsigned char *out, int *outl)
4101cc76114Stb {
4111cc76114Stb 	int i;
4121cc76114Stb 
4131cc76114Stb 	*outl = 0;
4141cc76114Stb 	if (ctx->num != 0) {
4151cc76114Stb 		i = EVP_DecodeBlock(out, ctx->enc_data, ctx->num);
4161cc76114Stb 		if (i < 0)
4171cc76114Stb 			return (-1);
4181cc76114Stb 		ctx->num = 0;
4191cc76114Stb 		*outl = i;
4201cc76114Stb 		return (1);
4211cc76114Stb 	} else
4221cc76114Stb 		return (1);
4231cc76114Stb }
424*9bac3682Sbeck LCRYPTO_ALIAS(EVP_DecodeFinal);
425