changeset 35839:c696bd1000c1 v9.1.0638

patch 9.1.0638: E1510 may happen when formatting a message for smsg() Commit: https://github.com/vim/vim/commit/0dff31576a340b74cec81517912923c38cb28450 Author: zeertzjq <zeertzjq@outlook.com> Date: Mon Jul 29 20:28:14 2024 +0200 patch 9.1.0638: E1510 may happen when formatting a message for smsg() Problem: E1510 may happen when formatting a message (after 9.1.0181). Solution: Only give E1510 when using typval. (zeertzjq) closes: #15391 Signed-off-by: zeertzjq <zeertzjq@outlook.com> Signed-off-by: Christian Brabandt <cb@256bit.org>
author Christian Brabandt <cb@256bit.org>
date Mon, 29 Jul 2024 20:30:04 +0200
parents ad072f6152bd
children 6af3ff2cfa38
files src/strings.c src/testdir/test_spellfile.vim src/version.c
diffstat 3 files changed, 51 insertions(+), 29 deletions(-) [+]
line wrap: on
line diff
--- a/src/strings.c
+++ b/src/strings.c
@@ -2497,7 +2497,8 @@ format_overflow_error(const char *pstart
 get_unsigned_int(
     const char *pstart,
     const char **p,
-    unsigned int *uj)
+    unsigned int *uj,
+    int overflow_err)
 {
     *uj = **p - '0';
     ++*p;
@@ -2510,8 +2511,13 @@ get_unsigned_int(
 
     if (*uj > MAX_ALLOWED_STRING_WIDTH)
     {
-	format_overflow_error(pstart);
-	return FAIL;
+	if (overflow_err)
+	{
+	    format_overflow_error(pstart);
+	    return FAIL;
+	}
+	else
+	    *uj = MAX_ALLOWED_STRING_WIDTH;
     }
 
     return OK;
@@ -2584,7 +2590,7 @@ parse_fmt_types(
 		// Positional argument
 		unsigned int uj;
 
-		if (get_unsigned_int(pstart, &p, &uj) == FAIL)
+		if (get_unsigned_int(pstart, &p, &uj, tvs != NULL) == FAIL)
 		    goto error;
 
 		pos_arg = uj;
@@ -2625,7 +2631,7 @@ parse_fmt_types(
 		    // Positional argument field width
 		    unsigned int uj;
 
-		    if (get_unsigned_int(arg + 1, &p, &uj) == FAIL)
+		    if (get_unsigned_int(arg + 1, &p, &uj, tvs != NULL) == FAIL)
 			goto error;
 
 		    if (*p != '$')
@@ -2656,7 +2662,7 @@ parse_fmt_types(
 		const char *digstart = p;
 		unsigned int uj;
 
-		if (get_unsigned_int(digstart, &p, &uj) == FAIL)
+		if (get_unsigned_int(digstart, &p, &uj, tvs != NULL) == FAIL)
 		    goto error;
 
 		if (*p == '$')
@@ -2680,7 +2686,7 @@ parse_fmt_types(
 			// Parse precision
 			unsigned int uj;
 
-			if (get_unsigned_int(arg + 1, &p, &uj) == FAIL)
+			if (get_unsigned_int(arg + 1, &p, &uj, tvs != NULL) == FAIL)
 			    goto error;
 
 			if (*p == '$')
@@ -2712,7 +2718,7 @@ parse_fmt_types(
 		    const char *digstart = p;
 		    unsigned int uj;
 
-		    if (get_unsigned_int(digstart, &p, &uj) == FAIL)
+		    if (get_unsigned_int(digstart, &p, &uj, tvs != NULL) == FAIL)
 			goto error;
 
 		    if (*p == '$')
@@ -3025,7 +3031,7 @@ vim_vsnprintf_typval(
 		const char *digstart = p;
 		unsigned int uj;
 
-		if (get_unsigned_int(digstart, &p, &uj) == FAIL)
+		if (get_unsigned_int(digstart, &p, &uj, tvs != NULL) == FAIL)
 		    goto error;
 
 		pos_arg = uj;
@@ -3067,7 +3073,7 @@ vim_vsnprintf_typval(
 		    // Positional argument field width
 		    unsigned int uj;
 
-		    if (get_unsigned_int(digstart, &p, &uj) == FAIL)
+		    if (get_unsigned_int(digstart, &p, &uj, tvs != NULL) == FAIL)
 			goto error;
 
 		    arg_idx = uj;
@@ -3085,8 +3091,13 @@ vim_vsnprintf_typval(
 
 		if (j > MAX_ALLOWED_STRING_WIDTH)
 		{
-		    format_overflow_error(digstart);
-		    goto error;
+		    if (tvs != NULL)
+		    {
+			format_overflow_error(digstart);
+			goto error;
+		    }
+		    else
+			j = MAX_ALLOWED_STRING_WIDTH;
 		}
 
 		if (j >= 0)
@@ -3104,15 +3115,9 @@ vim_vsnprintf_typval(
 		const char *digstart = p;
 		unsigned int uj;
 
-		if (get_unsigned_int(digstart, &p, &uj) == FAIL)
+		if (get_unsigned_int(digstart, &p, &uj, tvs != NULL) == FAIL)
 		    goto error;
 
-		if (uj > MAX_ALLOWED_STRING_WIDTH)
-		{
-		    format_overflow_error(digstart);
-		    goto error;
-		}
-
 		min_field_width = uj;
 	    }
 
@@ -3129,15 +3134,9 @@ vim_vsnprintf_typval(
 		    const char *digstart = p;
 		    unsigned int uj;
 
-		    if (get_unsigned_int(digstart, &p, &uj) == FAIL)
+		    if (get_unsigned_int(digstart, &p, &uj, tvs != NULL) == FAIL)
 			goto error;
 
-		    if (uj > MAX_ALLOWED_STRING_WIDTH)
-		    {
-			format_overflow_error(digstart);
-			goto error;
-		    }
-
 		    precision = uj;
 		}
 		else if (*p == '*')
@@ -3152,7 +3151,7 @@ vim_vsnprintf_typval(
 			// positional argument
 			unsigned int uj;
 
-			if (get_unsigned_int(digstart, &p, &uj) == FAIL)
+			if (get_unsigned_int(digstart, &p, &uj, tvs != NULL) == FAIL)
 			    goto error;
 
 			arg_idx = uj;
@@ -3170,8 +3169,13 @@ vim_vsnprintf_typval(
 
 		    if (j > MAX_ALLOWED_STRING_WIDTH)
 		    {
-			format_overflow_error(digstart);
-			goto error;
+			if (tvs != NULL)
+			{
+			    format_overflow_error(digstart);
+			    goto error;
+			}
+			else
+			    j = MAX_ALLOWED_STRING_WIDTH;
 		    }
 
 		    if (j >= 0)
--- a/src/testdir/test_spellfile.vim
+++ b/src/testdir/test_spellfile.vim
@@ -845,6 +845,22 @@ func Test_spell_add_word()
   %bw!
 endfunc
 
+func Test_spell_add_long_word()
+  set spell spellfile=./Xspellfile.add spelllang=en
+
+  let word = repeat('a', 9000)
+  let v:errmsg = ''
+  " Spell checking doesn't really work for such a long word,
+  " but this should not cause an E1510 error.
+  exe 'spellgood ' .. word
+  call assert_equal('', v:errmsg)
+  call assert_equal([word], readfile('./Xspellfile.add'))
+
+  set spell& spellfile= spelllang& encoding=utf-8
+  call delete('./Xspellfile.add')
+  call delete('./Xspellfile.add.spl')
+endfunc
+
 func Test_spellfile_verbose()
   call writefile(['1', 'one'], 'XtestVerbose.dic', 'D')
   call writefile([], 'XtestVerbose.aff', 'D')
--- a/src/version.c
+++ b/src/version.c
@@ -705,6 +705,8 @@ static char *(features[]) =
 static int included_patches[] =
 {   /* Add new patch number below this line */
 /**/
+    638,
+/**/
     637,
 /**/
     636,