104 lines
2.8 KiB
Diff
104 lines
2.8 KiB
Diff
From f6d39c31d2177549a986d170e192d8351bd571e2 Mon Sep 17 00:00:00 2001
|
|
From: Bram Moolenaar <Bram@vim.org>
|
|
Date: Tue, 16 Aug 2022 17:50:38 +0100
|
|
Subject: [PATCH] patch 9.0.0220: invalid memory access with for loop over NULL
|
|
string
|
|
|
|
Problem: Invalid memory access with for loop over NULL string.
|
|
Solution: Make sure mb_ptr2len() consistently returns zero for NUL.
|
|
---
|
|
src/globals.h | 3 ++-
|
|
src/mbyte.c | 21 +++++++++++++--------
|
|
src/testdir/test_eval_stuff.vim | 12 ++++++++++++
|
|
3 files changed, 27 insertions(+), 9 deletions(-)
|
|
|
|
diff --git a/src/globals.h b/src/globals.h
|
|
index 888f6e9..9b40be4 100644
|
|
--- a/src/globals.h
|
|
+++ b/src/globals.h
|
|
@@ -1033,7 +1033,8 @@ EXTERN vimconv_T output_conv; // type of output conversion
|
|
* (DBCS).
|
|
* The value is set in mb_init();
|
|
*/
|
|
-// length of char in bytes, including following composing chars
|
|
+// Length of char in bytes, including any following composing chars.
|
|
+// NUL has length zero.
|
|
EXTERN int (*mb_ptr2len)(char_u *p) INIT(= latin_ptr2len);
|
|
|
|
// idem, with limit on string length
|
|
diff --git a/src/mbyte.c b/src/mbyte.c
|
|
index 3656880..782a7ad 100644
|
|
--- a/src/mbyte.c
|
|
+++ b/src/mbyte.c
|
|
@@ -1077,24 +1077,28 @@ dbcs_char2bytes(int c, char_u *buf)
|
|
}
|
|
|
|
/*
|
|
- * mb_ptr2len() function pointer.
|
|
- * Get byte length of character at "*p" but stop at a NUL.
|
|
- * For UTF-8 this includes following composing characters.
|
|
- * Returns 0 when *p is NUL.
|
|
+ * Get byte length of character at "*p". Returns zero when "*p" is NUL.
|
|
+ * Used for mb_ptr2len() when 'encoding' latin.
|
|
*/
|
|
int
|
|
latin_ptr2len(char_u *p)
|
|
{
|
|
- return MB_BYTE2LEN(*p);
|
|
+ return *p == NUL ? 0 : 1;
|
|
}
|
|
|
|
+/*
|
|
+ * Get byte length of character at "*p". Returns zero when "*p" is NUL.
|
|
+ * Used for mb_ptr2len() when 'encoding' DBCS.
|
|
+ */
|
|
static int
|
|
-dbcs_ptr2len(
|
|
- char_u *p)
|
|
+dbcs_ptr2len(char_u *p)
|
|
{
|
|
int len;
|
|
|
|
- // Check if second byte is not missing.
|
|
+ if (*p == NUL)
|
|
+ return 0;
|
|
+
|
|
+ // if the second byte is missing the length is 1
|
|
len = MB_BYTE2LEN(*p);
|
|
if (len == 2 && p[1] == NUL)
|
|
len = 1;
|
|
@@ -2105,6 +2109,7 @@ utf_ptr2len_len(char_u *p, int size)
|
|
/*
|
|
* Return the number of bytes the UTF-8 encoding of the character at "p" takes.
|
|
* This includes following composing characters.
|
|
+ * Returns zero for NUL.
|
|
*/
|
|
int
|
|
utfc_ptr2len(char_u *p)
|
|
diff --git a/src/testdir/test_eval_stuff.vim b/src/testdir/test_eval_stuff.vim
|
|
index c63082e..313d791 100644
|
|
--- a/src/testdir/test_eval_stuff.vim
|
|
+++ b/src/testdir/test_eval_stuff.vim
|
|
@@ -75,6 +75,18 @@ func Test_for_invalid()
|
|
redraw
|
|
endfunc
|
|
|
|
+func Test_for_over_null_string()
|
|
+ let save_enc = &enc
|
|
+ set enc=iso8859
|
|
+ let cnt = 0
|
|
+ for c in test_null_string()
|
|
+ let cnt += 1
|
|
+ endfor
|
|
+ call assert_equal(0, cnt)
|
|
+
|
|
+ let &enc = save_enc
|
|
+endfunc
|
|
+
|
|
func Test_readfile_binary()
|
|
new
|
|
call setline(1, ['one', 'two', 'three'])
|
|
--
|
|
2.36.1
|
|
|