From: Aki Tuomi Date: Tue, 2 Apr 2019 10:09:48 +0000 (+0300) Subject: lib: json - Escape invalid UTF-8 as unicode bytes X-Git-Tag: 2.3.6~9 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=bc6df1eec16c0409a6500cd4d1380e8534e825fa;p=thirdparty%2Fdovecot%2Fcore.git lib: json - Escape invalid UTF-8 as unicode bytes This prevents dovecot from crashing if invalid UTF-8 input is given. --- diff --git a/src/lib/json-parser.c b/src/lib/json-parser.c index 9e0a871325..7a14a0bc87 100644 --- a/src/lib/json-parser.c +++ b/src/lib/json-parser.c @@ -821,9 +821,13 @@ void json_append_escaped_data(string_t *dest, const unsigned char *src, size_t s for (i = 0; i < size;) { bytes = uni_utf8_get_char_n(src+i, size-i, &chr); - /* refuse to add invalid data */ - i_assert(bytes > 0 && uni_is_valid_ucs4(chr)); - json_append_escaped_ucs4(dest, chr); - i += bytes; + if (bytes > 0 && uni_is_valid_ucs4(chr)) { + json_append_escaped_ucs4(dest, chr); + i += bytes; + } else { + str_append_data(dest, UNICODE_REPLACEMENT_CHAR_UTF8, + UTF8_REPLACEMENT_CHAR_LEN); + i++; + } } } diff --git a/src/lib/test-json-parser.c b/src/lib/test-json-parser.c index d130d79f4d..199be39e77 100644 --- a/src/lib/test-json-parser.c +++ b/src/lib/test-json-parser.c @@ -374,20 +374,20 @@ static void test_json_append_escaped(void) string_t *str = t_str_new(32); test_begin("json_append_escaped()"); - json_append_escaped(str, "\b\f\r\n\t\"\\\001\002-\xC3\xA4\xf0\x90\x90\xb7"); - test_assert(strcmp(str_c(str), "\\b\\f\\r\\n\\t\\\"\\\\\\u0001\\u0002-\\u00e4\\ud801\\udc37") == 0); + json_append_escaped(str, "\b\f\r\n\t\"\\\001\002-\xC3\xA4\xf0\x90\x90\xb7\xff"); + test_assert(strcmp(str_c(str), "\\b\\f\\r\\n\\t\\\"\\\\\\u0001\\u0002-\\u00e4\\ud801\\udc37" UNICODE_REPLACEMENT_CHAR_UTF8) == 0); test_end(); } static void test_json_append_escaped_data(void) { static const unsigned char test_input[] = - "\b\f\r\n\t\"\\\000\001\002-\xC3\xA4\xf0\x90\x90\xb7"; + "\b\f\r\n\t\"\\\000\001\002-\xC3\xA4\xf0\x90\x90\xb7\xff"; string_t *str = t_str_new(32); test_begin("json_append_escaped()"); json_append_escaped_data(str, test_input, sizeof(test_input)-1); - test_assert(strcmp(str_c(str), "\\b\\f\\r\\n\\t\\\"\\\\\\u0000\\u0001\\u0002-\\u00e4\\ud801\\udc37") == 0); + test_assert(strcmp(str_c(str), "\\b\\f\\r\\n\\t\\\"\\\\\\u0000\\u0001\\u0002-\\u00e4\\ud801\\udc37" UNICODE_REPLACEMENT_CHAR_UTF8) == 0); test_end(); }