Back to home page

LXR

 
 

    


File indexing completed on 2025-05-11 08:24:10

0001 /* SPDX-License-Identifier: ISC */
0002 
0003 /**
0004  * @file
0005  *
0006  * @ingroup RTEMSImplBase64
0007  *
0008  * @brief This source file contains the implementation of
0009  *   _Base64_Encode() and _Base64url_Encode().
0010  */
0011 
0012 /*
0013  * Copyright (C) 2020, 2024 embedded brains GmbH & Co. KG
0014  * Copyright (C) 2004, 2005, 2007, 2009  Internet Systems Consortium, Inc. ("ISC")
0015  * Copyright (C) 1998-2001, 2003  Internet Software Consortium.
0016  *
0017  * Permission to use, copy, modify, and/or distribute this software for any
0018  * purpose with or without fee is hereby granted, provided that the above
0019  * copyright notice and this permission notice appear in all copies.
0020  *
0021  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
0022  * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
0023  * AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
0024  * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
0025  * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
0026  * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
0027  * PERFORMANCE OF THIS SOFTWARE.
0028  */
0029 
0030 #include <rtems/base64.h>
0031 
0032 static void
0033 _Base64_Put(int c, void *arg, IO_Put_char put_char)
0034 {
0035     (*put_char)(c, arg);
0036 }
0037 
0038 static int
0039 _Base64_Do_encode(IO_Put_char put_char, void *arg, const void *src,
0040     size_t srclen, const char *wordbreak, int wordlen, const uint8_t *encoding)
0041 {
0042     unsigned int loops = 0;
0043     const unsigned char *in = src;
0044     int out = 0;
0045 
0046     if (wordlen < 4) {
0047         wordlen = 4;
0048     }
0049 
0050     while (srclen > 2) {
0051         _Base64_Put(encoding[(in[0]>>2)&0x3f], arg, put_char);
0052         _Base64_Put(encoding[((in[0]<<4)&0x30)|
0053                 ((in[1]>>4)&0x0f)], arg, put_char);
0054         _Base64_Put(encoding[((in[1]<<2)&0x3c)|
0055                 ((in[2]>>6)&0x03)], arg, put_char);
0056         _Base64_Put(encoding[in[2]&0x3f], arg, put_char);
0057         in += 3;
0058         srclen -= 3;
0059         out += 4;
0060 
0061         loops++;
0062         if (srclen != 0 &&
0063             (int)((loops + 1) * 4) >= wordlen)
0064         {
0065             const char *w = wordbreak;
0066             loops = 0;
0067             while (*w != '\0') {
0068                 _Base64_Put(*w, arg, put_char);
0069                 ++w;
0070                 ++out;
0071             }
0072         }
0073     }
0074     if (srclen == 2) {
0075         _Base64_Put(encoding[(in[0]>>2)&0x3f], arg, put_char);
0076         _Base64_Put(encoding[((in[0]<<4)&0x30)|
0077                 ((in[1]>>4)&0x0f)], arg, put_char);
0078         _Base64_Put(encoding[((in[1]<<2)&0x3c)], arg, put_char);
0079         _Base64_Put('=', arg, put_char);
0080         out += 4;
0081     } else if (srclen == 1) {
0082         _Base64_Put(encoding[(in[0]>>2)&0x3f], arg, put_char);
0083         _Base64_Put(encoding[((in[0]<<4)&0x30)], arg, put_char);
0084         _Base64_Put('=', arg, put_char);
0085         _Base64_Put('=', arg, put_char);
0086         out += 4;
0087     }
0088     return out;
0089 }
0090 
0091 const uint8_t _Base64_Encoding[64] = {
0092     'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O',
0093     'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd',
0094     'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's',
0095     't', 'u', 'v', 'w', 'x', 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7',
0096     '8', '9', '+', '/'
0097 };
0098 
0099 int
0100 _Base64_Encode(IO_Put_char put_char, void *arg, const void *src, size_t srclen,
0101     const char *wordbreak, int wordlen)
0102 {
0103     return _Base64_Do_encode(put_char, arg, src, srclen, wordbreak,
0104         wordlen, _Base64_Encoding);
0105 }
0106 
0107 const uint8_t _Base64url_Encoding[64] = {
0108     'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O',
0109     'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd',
0110     'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's',
0111     't', 'u', 'v', 'w', 'x', 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7',
0112     '8', '9', '-', '_'
0113 };
0114 
0115 int
0116 _Base64url_Encode(IO_Put_char put_char, void *arg, const void *src,
0117     size_t srclen, const char *wordbreak, int wordlen)
0118 {
0119     return _Base64_Do_encode(put_char, arg, src, srclen, wordbreak,
0120         wordlen, _Base64url_Encoding);
0121 }