mirror of
git://git.sv.gnu.org/emacs.git
synced 2026-02-16 17:24:23 +00:00
Add support for base64url variant of base-64 encoding/decoding
Implement the RFC4648 variant of base64 encoding used by URLs. * doc/lispref/text.texi (base64url-encode-region, base64url-encode-string): Document new functions. (base64-decode-region, base64-decode-string): Document new optional parameter 'base64url' used to use url variant when decoding data. * src/fns.c (base64url-encode-region, base64url-encode-region): New functions to manage url variant. (base64-decode-region, base64-decode-string): Add optional parameter to indicate use of url-variant. (base64_encode_region_1, base64_encode_string_1): Internal functions with extracted code from 'base64_encode_region' and 'base64_encode_string' and optional parameters to manage padding and url variant. (base64-encode-region, base64-encode-string) : Use base64_encode_region_1 and base64_encode_string_1. (base64-encode-1): Add parameters to manage padding and url variant. (base64-decode-1): Add parameter to manage url variant. * test/src/fns-tests.el (fns-tests--with-region): New helper macro to test region variant of base64 encode / decode functions. (fns-tests--string-repeat): Helper function used in base64 tests. (fns-tests-base64-encode-region, fns-tests-base64-encode-string): Tests for standard base64 function. (fns-test-base64url-encode-region, fns-test-base64url-encode-string): Tests for url variant. (fns-tests-base64-decode-string): Tests for decoding part.
This commit is contained in:
parent
faf10bd8eb
commit
7541b06872
3 changed files with 355 additions and 32 deletions
|
|
@ -4541,7 +4541,7 @@ Internet informational document describing a standard. RFCs are
|
|||
usually written by technical experts acting on their own initiative,
|
||||
and are traditionally written in a pragmatic, experience-driven
|
||||
manner.
|
||||
}2045. This section describes the functions for
|
||||
}2045 and also in RFC4648. This section describes the functions for
|
||||
converting to and from this code.
|
||||
|
||||
@deffn Command base64-encode-region beg end &optional no-line-break
|
||||
|
|
@ -4558,6 +4558,22 @@ text, to avoid overlong lines. However, if the optional argument
|
|||
the output is just one long line.
|
||||
@end deffn
|
||||
|
||||
@deffn Command base64url-encode-region beg end &optional no-pad
|
||||
This function converts the region from @var{beg} to @var{end} into base
|
||||
64 code. It returns the length of the encoded text. An error is
|
||||
signaled if a character in the region is multibyte, i.e., in a
|
||||
multibyte buffer the region must contain only characters from the
|
||||
charsets @code{ascii}, @code{eight-bit-control} and
|
||||
@code{eight-bit-graphic}.
|
||||
|
||||
Contrary to the function @code{base64-encode-region}, this function
|
||||
doesnt inserts newline characters into the encoded text, so the output
|
||||
is just one long line.
|
||||
|
||||
If the optional argument @var{no-pad} is non-@code{nil} then padding
|
||||
(@code{=}) isn't generated.
|
||||
@end deffn
|
||||
|
||||
@defun base64-encode-string string &optional no-line-break
|
||||
This function converts the string @var{string} into base 64 code. It
|
||||
returns a string containing the encoded text. As for
|
||||
|
|
@ -4570,20 +4586,40 @@ text, to avoid overlong lines. However, if the optional argument
|
|||
the result string is just one long line.
|
||||
@end defun
|
||||
|
||||
@deffn Command base64-decode-region beg end
|
||||
@defun base64url-encode-string string &optional no-pad
|
||||
This function converts the string @var{string} into base 64 url code
|
||||
(see RFC4648). It returns a string containing the encoded text. As
|
||||
for @code{base64url-encode-region}, an error is signaled if a
|
||||
character in the string is multibyte.
|
||||
|
||||
Contrary to @code{base64-encode-string}, this function doesnt inserts
|
||||
newline characters into the encoded text, so the result string is just
|
||||
one long line.
|
||||
|
||||
If the optional argument @var{no-pad} is non-@code{nil} then padding
|
||||
(@code{=}) isn't generated.
|
||||
@end defun
|
||||
|
||||
@deffn Command base64-decode-region beg end &optional base64url
|
||||
This function converts the region from @var{beg} to @var{end} from base
|
||||
64 code into the corresponding decoded text. It returns the length of
|
||||
the decoded text.
|
||||
|
||||
The decoding functions ignore newline characters in the encoded text.
|
||||
|
||||
If optional argument @var{base64url} is is non-@code{nil} then padding
|
||||
become optionnal and url variant is used (see RFC4648).
|
||||
@end deffn
|
||||
|
||||
@defun base64-decode-string string
|
||||
@defun base64-decode-string string &optional base64url
|
||||
This function converts the string @var{string} from base 64 code into
|
||||
the corresponding decoded text. It returns a unibyte string containing the
|
||||
decoded text.
|
||||
|
||||
The decoding functions ignore newline characters in the encoded text.
|
||||
|
||||
If optional argument @var{base64url} is is non-@code{nil} then padding
|
||||
become optionnal and url variant is used (see RFC4648).
|
||||
@end defun
|
||||
|
||||
@node Checksum/Hash
|
||||
|
|
|
|||
166
src/fns.c
166
src/fns.c
|
|
@ -3189,7 +3189,7 @@ The data read from the system are decoded using `locale-coding-system'. */)
|
|||
#define IS_ASCII(Character) \
|
||||
((Character) < 128)
|
||||
#define IS_BASE64(Character) \
|
||||
(IS_ASCII (Character) && base64_char_to_value[Character] >= 0)
|
||||
(IS_ASCII (Character) && b64_char_to_value[Character] >= 0)
|
||||
#define IS_BASE64_IGNORABLE(Character) \
|
||||
((Character) == ' ' || (Character) == '\t' || (Character) == '\n' \
|
||||
|| (Character) == '\f' || (Character) == '\r')
|
||||
|
|
@ -3222,6 +3222,17 @@ static const char base64_value_to_char[64] =
|
|||
'8', '9', '+', '/' /* 60-63 */
|
||||
};
|
||||
|
||||
static const char base64url_value_to_char[64] =
|
||||
{
|
||||
'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', /* 0- 9 */
|
||||
'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', /* 10-19 */
|
||||
'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd', /* 20-29 */
|
||||
'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', /* 30-39 */
|
||||
'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', /* 40-49 */
|
||||
'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7', /* 50-59 */
|
||||
'8', '9', '-', '_' /* 60-63 */
|
||||
};
|
||||
|
||||
/* Table of base64 values for first 128 characters. */
|
||||
static const short base64_char_to_value[128] =
|
||||
{
|
||||
|
|
@ -3240,6 +3251,23 @@ static const short base64_char_to_value[128] =
|
|||
49, 50, 51, -1, -1, -1, -1, -1 /* 120-127 */
|
||||
};
|
||||
|
||||
static const short base64url_char_to_value[128] =
|
||||
{
|
||||
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 0- 9 */
|
||||
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 10- 19 */
|
||||
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 20- 29 */
|
||||
-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 30- 39 */
|
||||
-1, -1, -1, -1, -1, 62, -1, -1, 52, 53, /* 40- 49 */
|
||||
54, 55, 56, 57, 58, 59, 60, 61, -1, -1, /* 50- 59 */
|
||||
-1, -1, -1, -1, -1, 0, 1, 2, 3, 4, /* 60- 69 */
|
||||
5, 6, 7, 8, 9, 10, 11, 12, 13, 14, /* 70- 79 */
|
||||
15, 16, 17, 18, 19, 20, 21, 22, 23, 24, /* 80- 89 */
|
||||
25, -1, -1, -1, -1, 63, -1, 26, 27, 28, /* 90- 99 */
|
||||
29, 30, 31, 32, 33, 34, 35, 36, 37, 38, /* 100-109 */
|
||||
39, 40, 41, 42, 43, 44, 45, 46, 47, 48, /* 110-119 */
|
||||
49, 50, 51, -1, -1, -1, -1, -1 /* 120-127 */
|
||||
};
|
||||
|
||||
/* The following diagram shows the logical steps by which three octets
|
||||
get transformed into four base64 characters.
|
||||
|
||||
|
|
@ -3259,9 +3287,17 @@ static const short base64_char_to_value[128] =
|
|||
base64 characters. */
|
||||
|
||||
|
||||
static ptrdiff_t base64_encode_1 (const char *, char *, ptrdiff_t, bool, bool);
|
||||
static ptrdiff_t base64_encode_1 (const char *, char *, ptrdiff_t, bool, bool,
|
||||
bool, bool);
|
||||
static ptrdiff_t base64_decode_1 (const char *, char *, ptrdiff_t, bool,
|
||||
ptrdiff_t *);
|
||||
bool, ptrdiff_t *);
|
||||
|
||||
Lisp_Object base64_encode_region_1 (Lisp_Object, Lisp_Object, bool,
|
||||
bool, bool);
|
||||
|
||||
Lisp_Object base64_encode_string_1(Lisp_Object, bool,
|
||||
bool, bool);
|
||||
|
||||
|
||||
DEFUN ("base64-encode-region", Fbase64_encode_region, Sbase64_encode_region,
|
||||
2, 3, "r",
|
||||
|
|
@ -3270,6 +3306,26 @@ Return the length of the encoded text.
|
|||
Optional third argument NO-LINE-BREAK means do not break long lines
|
||||
into shorter lines. */)
|
||||
(Lisp_Object beg, Lisp_Object end, Lisp_Object no_line_break)
|
||||
{
|
||||
return base64_encode_region_1(beg, end, NILP (no_line_break), true, false);
|
||||
}
|
||||
|
||||
|
||||
DEFUN ("base64url-encode-region", Fbase64url_encode_region, Sbase64url_encode_region,
|
||||
2, 3, "r",
|
||||
doc: /* Base64url-encode the region between BEG and END.
|
||||
Return the length of the encoded text.
|
||||
Optional second argument NO-PAD means do not add padding char =.
|
||||
|
||||
This is the variant defined in RFC4648. */)
|
||||
(Lisp_Object beg, Lisp_Object end, Lisp_Object no_pad)
|
||||
{
|
||||
return base64_encode_region_1(beg, end, false, NILP(no_pad), true);
|
||||
}
|
||||
|
||||
Lisp_Object
|
||||
base64_encode_region_1 (Lisp_Object beg, Lisp_Object end, bool line_break,
|
||||
bool pad, bool base64url)
|
||||
{
|
||||
char *encoded;
|
||||
ptrdiff_t allength, length;
|
||||
|
|
@ -3292,7 +3348,8 @@ into shorter lines. */)
|
|||
|
||||
encoded = SAFE_ALLOCA (allength);
|
||||
encoded_length = base64_encode_1 ((char *) BYTE_POS_ADDR (ibeg),
|
||||
encoded, length, NILP (no_line_break),
|
||||
encoded, length, line_break,
|
||||
pad, base64url,
|
||||
!NILP (BVAR (current_buffer, enable_multibyte_characters)));
|
||||
if (encoded_length > allength)
|
||||
emacs_abort ();
|
||||
|
|
@ -3330,6 +3387,26 @@ Optional second argument NO-LINE-BREAK means do not break long lines
|
|||
into shorter lines. */)
|
||||
(Lisp_Object string, Lisp_Object no_line_break)
|
||||
{
|
||||
|
||||
return base64_encode_string_1(string, NILP (no_line_break), true, false);
|
||||
}
|
||||
|
||||
DEFUN ("base64url-encode-string", Fbase64url_encode_string, Sbase64url_encode_string,
|
||||
1, 2, 0,
|
||||
doc: /* Base64url-encode STRING and return the result.
|
||||
Optional second argument NO-PAD means do not add padding char =.
|
||||
|
||||
This is the variant defined in RFC4648. */)
|
||||
(Lisp_Object string, Lisp_Object no_pad)
|
||||
{
|
||||
|
||||
return base64_encode_string_1(string, false, NILP(no_pad), true);
|
||||
}
|
||||
|
||||
Lisp_Object
|
||||
base64_encode_string_1(Lisp_Object string, bool line_break,
|
||||
bool pad, bool base64url)
|
||||
{
|
||||
ptrdiff_t allength, length, encoded_length;
|
||||
char *encoded;
|
||||
Lisp_Object encoded_string;
|
||||
|
|
@ -3348,7 +3425,8 @@ into shorter lines. */)
|
|||
encoded = SAFE_ALLOCA (allength);
|
||||
|
||||
encoded_length = base64_encode_1 (SSDATA (string),
|
||||
encoded, length, NILP (no_line_break),
|
||||
encoded, length, line_break,
|
||||
pad, base64url,
|
||||
STRING_MULTIBYTE (string));
|
||||
if (encoded_length > allength)
|
||||
emacs_abort ();
|
||||
|
|
@ -3367,7 +3445,8 @@ into shorter lines. */)
|
|||
|
||||
static ptrdiff_t
|
||||
base64_encode_1 (const char *from, char *to, ptrdiff_t length,
|
||||
bool line_break, bool multibyte)
|
||||
bool line_break, bool pad, bool base64url,
|
||||
bool multibyte)
|
||||
{
|
||||
int counter = 0;
|
||||
ptrdiff_t i = 0;
|
||||
|
|
@ -3375,6 +3454,7 @@ base64_encode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
int c;
|
||||
unsigned int value;
|
||||
int bytes;
|
||||
char const *b64_value_to_char = (base64url) ? base64url_value_to_char : base64_value_to_char;
|
||||
|
||||
while (i < length)
|
||||
{
|
||||
|
|
@ -3405,16 +3485,19 @@ base64_encode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
|
||||
/* Process first byte of a triplet. */
|
||||
|
||||
*e++ = base64_value_to_char[0x3f & c >> 2];
|
||||
*e++ = b64_value_to_char[0x3f & c >> 2];
|
||||
value = (0x03 & c) << 4;
|
||||
|
||||
/* Process second byte of a triplet. */
|
||||
|
||||
if (i == length)
|
||||
{
|
||||
*e++ = base64_value_to_char[value];
|
||||
*e++ = '=';
|
||||
*e++ = '=';
|
||||
*e++ = b64_value_to_char[value];
|
||||
if (pad)
|
||||
{
|
||||
*e++ = '=';
|
||||
*e++ = '=';
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
|
|
@ -3430,15 +3513,18 @@ base64_encode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
else
|
||||
c = from[i++];
|
||||
|
||||
*e++ = base64_value_to_char[value | (0x0f & c >> 4)];
|
||||
*e++ = b64_value_to_char[value | (0x0f & c >> 4)];
|
||||
value = (0x0f & c) << 2;
|
||||
|
||||
/* Process third byte of a triplet. */
|
||||
|
||||
if (i == length)
|
||||
{
|
||||
*e++ = base64_value_to_char[value];
|
||||
*e++ = '=';
|
||||
*e++ = b64_value_to_char[value];
|
||||
if (pad)
|
||||
{
|
||||
*e++ = '=';
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
|
|
@ -3454,8 +3540,8 @@ base64_encode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
else
|
||||
c = from[i++];
|
||||
|
||||
*e++ = base64_value_to_char[value | (0x03 & c >> 6)];
|
||||
*e++ = base64_value_to_char[0x3f & c];
|
||||
*e++ = b64_value_to_char[value | (0x03 & c >> 6)];
|
||||
*e++ = b64_value_to_char[0x3f & c];
|
||||
}
|
||||
|
||||
return e - to;
|
||||
|
|
@ -3463,11 +3549,13 @@ base64_encode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
|
||||
|
||||
DEFUN ("base64-decode-region", Fbase64_decode_region, Sbase64_decode_region,
|
||||
2, 2, "r",
|
||||
2, 3, "r",
|
||||
doc: /* Base64-decode the region between BEG and END.
|
||||
Return the length of the decoded text.
|
||||
If the region can't be decoded, signal an error and don't modify the buffer. */)
|
||||
(Lisp_Object beg, Lisp_Object end)
|
||||
If the region can't be decoded, signal an error and don't modify the buffer.
|
||||
Optional third argument BASE64URL define if base64Url variant will be used
|
||||
see RFC4648. */)
|
||||
(Lisp_Object beg, Lisp_Object end, Lisp_Object base64url)
|
||||
{
|
||||
ptrdiff_t ibeg, iend, length, allength;
|
||||
char *decoded;
|
||||
|
|
@ -3492,7 +3580,7 @@ If the region can't be decoded, signal an error and don't modify the buffer. */
|
|||
|
||||
move_gap_both (XFIXNAT (beg), ibeg);
|
||||
decoded_length = base64_decode_1 ((char *) BYTE_POS_ADDR (ibeg),
|
||||
decoded, length,
|
||||
decoded, length, !NILP (base64url),
|
||||
multibyte, &inserted_chars);
|
||||
if (decoded_length > allength)
|
||||
emacs_abort ();
|
||||
|
|
@ -3526,9 +3614,11 @@ If the region can't be decoded, signal an error and don't modify the buffer. */
|
|||
}
|
||||
|
||||
DEFUN ("base64-decode-string", Fbase64_decode_string, Sbase64_decode_string,
|
||||
1, 1, 0,
|
||||
doc: /* Base64-decode STRING and return the result. */)
|
||||
(Lisp_Object string)
|
||||
1, 2, 0,
|
||||
doc: /* Base64-decode STRING and return the result
|
||||
Optional argument BASE64URL define if base64Url variant will be used
|
||||
see RFC4648. */)
|
||||
(Lisp_Object string, Lisp_Object base64url)
|
||||
{
|
||||
char *decoded;
|
||||
ptrdiff_t length, decoded_length;
|
||||
|
|
@ -3543,7 +3633,7 @@ DEFUN ("base64-decode-string", Fbase64_decode_string, Sbase64_decode_string,
|
|||
|
||||
/* The decoded result should be unibyte. */
|
||||
decoded_length = base64_decode_1 (SSDATA (string), decoded, length,
|
||||
0, NULL);
|
||||
!NILP (base64url), 0, NULL);
|
||||
if (decoded_length > length)
|
||||
emacs_abort ();
|
||||
else if (decoded_length >= 0)
|
||||
|
|
@ -3565,6 +3655,7 @@ DEFUN ("base64-decode-string", Fbase64_decode_string, Sbase64_decode_string,
|
|||
|
||||
static ptrdiff_t
|
||||
base64_decode_1 (const char *from, char *to, ptrdiff_t length,
|
||||
bool base64url,
|
||||
bool multibyte, ptrdiff_t *nchars_return)
|
||||
{
|
||||
ptrdiff_t i = 0; /* Used inside READ_QUADRUPLET_BYTE */
|
||||
|
|
@ -3572,6 +3663,7 @@ base64_decode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
unsigned char c;
|
||||
unsigned long value;
|
||||
ptrdiff_t nchars = 0;
|
||||
short const *b64_char_to_value = (base64url) ? base64url_char_to_value : base64_char_to_value;
|
||||
|
||||
while (1)
|
||||
{
|
||||
|
|
@ -3581,7 +3673,7 @@ base64_decode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
|
||||
if (!IS_BASE64 (c))
|
||||
return -1;
|
||||
value = base64_char_to_value[c] << 18;
|
||||
value = b64_char_to_value[c] << 18;
|
||||
|
||||
/* Process second byte of a quadruplet. */
|
||||
|
||||
|
|
@ -3589,7 +3681,7 @@ base64_decode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
|
||||
if (!IS_BASE64 (c))
|
||||
return -1;
|
||||
value |= base64_char_to_value[c] << 12;
|
||||
value |= b64_char_to_value[c] << 12;
|
||||
|
||||
c = (unsigned char) (value >> 16);
|
||||
if (multibyte && c >= 128)
|
||||
|
|
@ -3600,7 +3692,14 @@ base64_decode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
|
||||
/* Process third byte of a quadruplet. */
|
||||
|
||||
READ_QUADRUPLET_BYTE (-1);
|
||||
if (!base64url)
|
||||
{
|
||||
READ_QUADRUPLET_BYTE (-1);
|
||||
}
|
||||
else
|
||||
{
|
||||
READ_QUADRUPLET_BYTE (e-to);
|
||||
}
|
||||
|
||||
if (c == '=')
|
||||
{
|
||||
|
|
@ -3613,7 +3712,7 @@ base64_decode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
|
||||
if (!IS_BASE64 (c))
|
||||
return -1;
|
||||
value |= base64_char_to_value[c] << 6;
|
||||
value |= b64_char_to_value[c] << 6;
|
||||
|
||||
c = (unsigned char) (0xff & value >> 8);
|
||||
if (multibyte && c >= 128)
|
||||
|
|
@ -3624,14 +3723,21 @@ base64_decode_1 (const char *from, char *to, ptrdiff_t length,
|
|||
|
||||
/* Process fourth byte of a quadruplet. */
|
||||
|
||||
READ_QUADRUPLET_BYTE (-1);
|
||||
if (!base64url)
|
||||
{
|
||||
READ_QUADRUPLET_BYTE (-1);
|
||||
}
|
||||
else
|
||||
{
|
||||
READ_QUADRUPLET_BYTE (e-to);
|
||||
}
|
||||
|
||||
if (c == '=')
|
||||
continue;
|
||||
|
||||
if (!IS_BASE64 (c))
|
||||
return -1;
|
||||
value |= base64_char_to_value[c];
|
||||
value |= b64_char_to_value[c];
|
||||
|
||||
c = (unsigned char) (0xff & value);
|
||||
if (multibyte && c >= 128)
|
||||
|
|
@ -5461,6 +5567,8 @@ this variable. */);
|
|||
defsubr (&Sbase64_decode_region);
|
||||
defsubr (&Sbase64_encode_string);
|
||||
defsubr (&Sbase64_decode_string);
|
||||
defsubr (&Sbase64url_encode_region);
|
||||
defsubr (&Sbase64url_encode_string);
|
||||
defsubr (&Smd5);
|
||||
defsubr (&Ssecure_hash_algorithms);
|
||||
defsubr (&Ssecure_hash);
|
||||
|
|
|
|||
|
|
@ -233,6 +233,185 @@
|
|||
(should (equal (func-arity (eval (lambda (x &optional y)) t)) '(1 . 2)))
|
||||
(should (equal (func-arity 'let) '(1 . unevalled))))
|
||||
|
||||
(defun fns-tests--string-repeat (s o)
|
||||
(apply 'concat (make-list o s)))
|
||||
|
||||
(defmacro fns-tests--with-region (funcname string &rest args)
|
||||
"Apply FUNCNAME in a temp bufer on the region produced by STRING."
|
||||
(declare (indent 1))
|
||||
`(with-temp-buffer
|
||||
(insert ,string)
|
||||
(,funcname (point-min) (point-max) ,@args)
|
||||
(buffer-string)))
|
||||
|
||||
(ert-deftest fns-tests-base64-encode-region ()
|
||||
;; standard variant RFC2045
|
||||
(should (equal (fns-tests--with-region base64-encode-region "") ""))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "f") "Zg=="))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "fo") "Zm8="))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "foo") "Zm9v"))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "foob") "Zm9vYg=="))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "fooba") "Zm9vYmE="))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "foobar") "Zm9vYmFy"))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "\x14\xfb\x9c\x03\xd9\x7e") "FPucA9l+"))
|
||||
(should (equal (fns-tests--with-region base64-encode-region "\x14\xfb\x9c\x03\xd9\x7f") "FPucA9l/")))
|
||||
|
||||
(ert-deftest fns-tests-base64-encode-string ()
|
||||
;; standard variant RFC2045
|
||||
(should (equal (base64-encode-string "") ""))
|
||||
(should (equal (base64-encode-string "f") "Zg=="))
|
||||
(should (equal (base64-encode-string "fo") "Zm8="))
|
||||
(should (equal (base64-encode-string "foo") "Zm9v"))
|
||||
(should (equal (base64-encode-string "foob") "Zm9vYg=="))
|
||||
(should (equal (base64-encode-string "fooba") "Zm9vYmE="))
|
||||
(should (equal (base64-encode-string "foobar") "Zm9vYmFy"))
|
||||
(should (equal (base64-encode-string "\x14\xfb\x9c\x03\xd9\x7e") "FPucA9l+"))
|
||||
(should (equal (base64-encode-string "\x14\xfb\x9c\x03\xd9\x7f") "FPucA9l/")))
|
||||
|
||||
(ert-deftest fns-test-base64url-encode-region ()
|
||||
;; url variant wih padding
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "") ""))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "f") "Zg=="))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "fo") "Zm8="))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "foo") "Zm9v"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "foob") "Zm9vYg=="))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "fooba") "Zm9vYmE="))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "foobar") "Zm9vYmFy"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "\x14\xfb\x9c\x03\xd9\x7e") "FPucA9l-"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "\x14\xfb\x9c\x03\xd9\x7f") "FPucA9l_"))
|
||||
|
||||
;; url variant no padding
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "" t) ""))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "f" t) "Zg"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "fo" t) "Zm8"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "foo" t) "Zm9v"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "foob" t) "Zm9vYg"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "fooba" t) "Zm9vYmE"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "foobar" t) "Zm9vYmFy"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "\x14\xfb\x9c\x03\xd9\x7e" t) "FPucA9l-"))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region "\x14\xfb\x9c\x03\xd9\x7f" t) "FPucA9l_"))
|
||||
|
||||
|
||||
;; url variant no line break no padding
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "f" 100) t)
|
||||
(concat (fns-tests--string-repeat "Zm" 66) "Zg")))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "fo" 50) t)
|
||||
(concat (fns-tests--string-repeat "Zm9mb2Zv" 16) "Zm9mbw")))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "foo" 25) t)
|
||||
(fns-tests--string-repeat "Zm9v" 25)))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "foob" 15) t)
|
||||
(fns-tests--string-repeat "Zm9vYmZvb2Jmb29i" 5)))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "fooba" 15) t)
|
||||
(fns-tests--string-repeat "Zm9vYmFmb29iYWZvb2Jh" 5)))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "foobar" 15) t)
|
||||
(concat (fns-tests--string-repeat "Zm9vYmFyZm9vYmFy" 7) "Zm9vYmFy")))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "\x14\xfb\x9c\x03\xd9\x7e" 10) t)
|
||||
(fns-tests--string-repeat "FPucA9l-" 10)))
|
||||
(should (equal (fns-tests--with-region base64url-encode-region (fns-tests--string-repeat "\x14\xfb\x9c\x03\xd9\x7f" 10) t)
|
||||
(fns-tests--string-repeat "FPucA9l_" 10))))
|
||||
|
||||
(ert-deftest fns-test-base64url-encode-string ()
|
||||
;; url variant wih padding
|
||||
(should (equal (base64url-encode-string "") ""))
|
||||
(should (equal (base64url-encode-string "f") "Zg=="))
|
||||
(should (equal (base64url-encode-string "fo") "Zm8="))
|
||||
(should (equal (base64url-encode-string "foo") "Zm9v"))
|
||||
(should (equal (base64url-encode-string "foob") "Zm9vYg=="))
|
||||
(should (equal (base64url-encode-string "fooba") "Zm9vYmE="))
|
||||
(should (equal (base64url-encode-string "foobar") "Zm9vYmFy"))
|
||||
(should (equal (base64url-encode-string "\x14\xfb\x9c\x03\xd9\x7e") "FPucA9l-"))
|
||||
(should (equal (base64url-encode-string "\x14\xfb\x9c\x03\xd9\x7f") "FPucA9l_"))
|
||||
|
||||
;; url variant no padding
|
||||
(should (equal (base64url-encode-string "" t) ""))
|
||||
(should (equal (base64url-encode-string "f" t) "Zg"))
|
||||
(should (equal (base64url-encode-string "fo" t) "Zm8"))
|
||||
(should (equal (base64url-encode-string "foo" t) "Zm9v"))
|
||||
(should (equal (base64url-encode-string "foob" t) "Zm9vYg"))
|
||||
(should (equal (base64url-encode-string "fooba" t) "Zm9vYmE"))
|
||||
(should (equal (base64url-encode-string "foobar" t) "Zm9vYmFy"))
|
||||
(should (equal (base64url-encode-string "\x14\xfb\x9c\x03\xd9\x7e" t) "FPucA9l-"))
|
||||
(should (equal (base64url-encode-string "\x14\xfb\x9c\x03\xd9\x7f" t) "FPucA9l_"))
|
||||
|
||||
|
||||
;; url variant no line break no padding
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "f" 100) t) (concat (fns-tests--string-repeat "Zm" 66) "Zg")))
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "fo" 50) t) (concat (fns-tests--string-repeat "Zm9mb2Zv" 16) "Zm9mbw")))
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "foo" 25) t) (fns-tests--string-repeat "Zm9v" 25)))
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "foob" 15) t) (fns-tests--string-repeat "Zm9vYmZvb2Jmb29i" 5)))
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "fooba" 15) t) (fns-tests--string-repeat "Zm9vYmFmb29iYWZvb2Jh" 5)))
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "foobar" 15) t) (concat (fns-tests--string-repeat "Zm9vYmFyZm9vYmFy" 7) "Zm9vYmFy")))
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "\x14\xfb\x9c\x03\xd9\x7e" 10) t) (fns-tests--string-repeat "FPucA9l-" 10)))
|
||||
(should (equal (base64url-encode-string (fns-tests--string-repeat "\x14\xfb\x9c\x03\xd9\x7f" 10) t) (fns-tests--string-repeat "FPucA9l_" 10))))
|
||||
|
||||
(ert-deftest fns-tests-base64-decode-string ()
|
||||
;; standard variant RFC2045
|
||||
(should (equal (base64-decode-string "") ""))
|
||||
(should (equal (base64-decode-string "Zg==") "f"))
|
||||
(should (equal (base64-decode-string "Zm8=") "fo"))
|
||||
(should (equal (base64-decode-string "Zm9v") "foo"))
|
||||
(should (equal (base64-decode-string "Zm9vYg==") "foob"))
|
||||
(should (equal (base64-decode-string "Zm9vYmE=") "fooba"))
|
||||
(should (equal (base64-decode-string "Zm9vYmFy") "foobar"))
|
||||
(should (equal (base64-decode-string "FPucA9l+") "\x14\xfb\x9c\x03\xd9\x7e"))
|
||||
(should (equal (base64-decode-string "FPucA9l/") "\x14\xfb\x9c\x03\xd9\x7f"))
|
||||
|
||||
;; no paddign
|
||||
(should (equal (base64-decode-string "" t) ""))
|
||||
(should (equal (base64-decode-string "Zg" t) "f"))
|
||||
(should (equal (base64-decode-string "Zm8" t) "fo"))
|
||||
(should (equal (base64-decode-string "Zm9v" t) "foo"))
|
||||
(should (equal (base64-decode-string "Zm9vYg" t) "foob"))
|
||||
(should (equal (base64-decode-string "Zm9vYmE" t) "fooba"))
|
||||
(should (equal (base64-decode-string "Zm9vYmFy" t) "foobar"))
|
||||
|
||||
;; url variant wih padding
|
||||
(should (equal (base64-decode-string "") ""))
|
||||
(should (equal (base64-decode-string "Zg==" t) "f") )
|
||||
(should (equal (base64-decode-string "Zm8=" t) "fo"))
|
||||
(should (equal (base64-decode-string "Zm9v" t) "foo"))
|
||||
(should (equal (base64-decode-string "Zm9vYg==" t) "foob"))
|
||||
(should (equal (base64-decode-string "Zm9vYmE=" t) "fooba"))
|
||||
(should (equal (base64-decode-string "Zm9vYmFy" t) "foobar"))
|
||||
(should (equal (base64-decode-string "FPucA9l-" t) "\x14\xfb\x9c\x03\xd9\x7e"))
|
||||
(should (equal (base64-decode-string "FPucA9l_" t) "\x14\xfb\x9c\x03\xd9\x7f"))
|
||||
|
||||
;; url variant no padding
|
||||
(should (equal (base64-decode-string "") ""))
|
||||
(should (equal (base64-decode-string "Zg" t) "f"))
|
||||
(should (equal (base64-decode-string "Zm8" t) "fo"))
|
||||
(should (equal (base64-decode-string "Zm9v" t) "foo"))
|
||||
(should (equal (base64-decode-string "Zm9vYg" t) "foob"))
|
||||
(should (equal (base64-decode-string "Zm9vYmE" t) "fooba"))
|
||||
(should (equal (base64-decode-string "Zm9vYmFy" t) "foobar"))
|
||||
(should (equal (base64-decode-string "FPucA9l-" t) "\x14\xfb\x9c\x03\xd9\x7e"))
|
||||
(should (equal (base64-decode-string "FPucA9l_" t) "\x14\xfb\x9c\x03\xd9\x7f"))
|
||||
|
||||
|
||||
;; url variant no line break no padding
|
||||
(should (equal (base64-decode-string (concat (fns-tests--string-repeat "Zm" 66) "Zg") t)
|
||||
(fns-tests--string-repeat "f" 100)))
|
||||
(should (equal (base64-decode-string (concat (fns-tests--string-repeat "Zm9mb2Zv" 16) "Zm9mbw") t)
|
||||
(fns-tests--string-repeat "fo" 50)))
|
||||
(should (equal (base64-decode-string (fns-tests--string-repeat "Zm9v" 25) t)
|
||||
(fns-tests--string-repeat "foo" 25)))
|
||||
(should (equal (base64-decode-string (fns-tests--string-repeat "Zm9vYmZvb2Jmb29i" 5) t)
|
||||
(fns-tests--string-repeat "foob" 15)))
|
||||
(should (equal (base64-decode-string (fns-tests--string-repeat "Zm9vYmFmb29iYWZvb2Jh" 5) t)
|
||||
(fns-tests--string-repeat "fooba" 15)))
|
||||
(should (equal (base64-decode-string (concat (fns-tests--string-repeat "Zm9vYmFyZm9vYmFy" 7) "Zm9vYmFy") t)
|
||||
(fns-tests--string-repeat "foobar" 15)))
|
||||
(should (equal (base64-decode-string (fns-tests--string-repeat "FPucA9l-" 10) t)
|
||||
(fns-tests--string-repeat "\x14\xfb\x9c\x03\xd9\x7e" 10)))
|
||||
(should (equal (base64-decode-string (fns-tests--string-repeat "FPucA9l_" 10) t)
|
||||
(fns-tests--string-repeat "\x14\xfb\x9c\x03\xd9\x7f" 10)))
|
||||
|
||||
;; errors check
|
||||
(should (eq :got-error (condition-case () (base64-decode-string "Zg=") (error :got-error))))
|
||||
(should (eq :got-error (condition-case () (base64-decode-string "Zm9vYmE") (error :got-error))))
|
||||
(should (eq :got-error (condition-case () (base64-decode-string "Zm9vYmFy=") (error :got-error))))
|
||||
(should (eq :got-error (condition-case () (base64-decode-string "Zg=Zg=") (error :got-error)))))
|
||||
|
||||
(ert-deftest fns-tests-hash-buffer ()
|
||||
(should (equal (sha1 "foo") "0beec7b5ea3f0fdbc95d0dd47f3c5bc275da8a33"))
|
||||
(should (equal (with-temp-buffer
|
||||
|
|
|
|||
Loading…
Reference in a new issue