changeset 35710:c9eeff724dc4 v9.1.0590

patch 9.1.0590: Vim9: crash when accessing getregionpos() return value Commit: https://github.com/vim/vim/commit/d4d120720862ba21654e614d975d21738f8a02e4 Author: zeertzjq <zeertzjq@outlook.com> Date: Tue Jul 16 20:34:16 2024 +0200 patch 9.1.0590: Vim9: crash when accessing getregionpos() return value Problem: Vim9: crash when accessing getregionpos() return value. Solution: Correct the return type (zeertzjq). fixes: #15272 closes: #15273 Signed-off-by: zeertzjq <zeertzjq@outlook.com> Signed-off-by: Christian Brabandt <cb@256bit.org>
author Christian Brabandt <cb@256bit.org>
date Wed, 17 Jul 2024 08:13:55 +0200
parents 88ab4f4219b7
children 960025b0bcc9
files runtime/doc/builtin.txt src/evalfunc.c src/globals.h src/testdir/test_vim9_builtin.vim src/version.c
diffstat 5 files changed, 68 insertions(+), 32 deletions(-) [+]
line wrap: on
line diff
--- a/runtime/doc/builtin.txt
+++ b/runtime/doc/builtin.txt
@@ -1,4 +1,4 @@
-*builtin.txt*	For Vim version 9.1.  Last change: 2024 Jul 11
+*builtin.txt*	For Vim version 9.1.  Last change: 2024 Jul 16
 
 
 		  VIM REFERENCE MANUAL	  by Bram Moolenaar
@@ -4804,6 +4804,8 @@ getregion({pos1}, {pos2} [, {opts}])			*
 <
 		Can also be used as a |method|: >
 			getpos('.')->getregion(getpos("'a"))
+<
+		Return type: list<string>
 
 <
 getregionpos({pos1}, {pos2} [, {opts}])            *getregionpos()*
@@ -4841,7 +4843,7 @@ getregionpos({pos1}, {pos2} [, {opts}]) 
 		Can also be used as a |method|: >
 			getpos('.')->getregionpos(getpos("'a"))
 <
-		Return type: list<string>
+		Return type: list<list<list<number>>>
 
 
 getregtype([{regname}])					*getregtype()*
--- a/src/evalfunc.c
+++ b/src/evalfunc.c
@@ -1326,7 +1326,6 @@ ret_list_items(int argcount UNUSED,
     *decl_type = &t_list_any;
     return &t_list_list_any;
 }
-
     static type_T *
 ret_list_string_items(int argcount UNUSED,
 	type2_T *argtypes UNUSED,
@@ -1336,6 +1335,14 @@ ret_list_string_items(int argcount UNUSE
     return &t_list_list_string;
 }
     static type_T *
+ret_list_regionpos(int argcount UNUSED,
+	type2_T *argtypes UNUSED,
+	type_T	**decl_type)
+{
+    *decl_type = &t_list_any;
+    return &t_list_list_list_number;
+}
+    static type_T *
 ret_dict_any(int argcount UNUSED,
 	type2_T *argtypes UNUSED,
 	type_T	**decl_type UNUSED)
@@ -1968,11 +1975,11 @@ static funcentry_T global_functions[] =
 			ret_number,	    f_diff_hlID},
     {"digraph_get",	1, 1, FEARG_1,	    arg1_string,
 			ret_string,	    f_digraph_get},
-    {"digraph_getlist",0, 1, FEARG_1,	    arg1_bool,
+    {"digraph_getlist",	0, 1, FEARG_1,	    arg1_bool,
 			ret_list_string_items, f_digraph_getlist},
     {"digraph_set",	2, 2, FEARG_1,	    arg2_string,
 			ret_bool,	f_digraph_set},
-    {"digraph_setlist",1, 1, FEARG_1,	    arg1_list_string,
+    {"digraph_setlist",	1, 1, FEARG_1,	    arg1_list_string,
 			ret_bool,	    f_digraph_setlist},
     {"echoraw",		1, 1, FEARG_1,	    arg1_string,
 			ret_void,	    f_echoraw},
@@ -2144,8 +2151,8 @@ static funcentry_T global_functions[] =
 			ret_dict_any,	    f_getreginfo},
     {"getregion",	2, 3, FEARG_1,	    arg3_list_list_dict,
 			ret_list_string,    f_getregion},
-    {"getregionpos",   2, 3, FEARG_1,      arg3_list_list_dict,
-			ret_list_string,    f_getregionpos},
+    {"getregionpos",	2, 3, FEARG_1,      arg3_list_list_dict,
+			ret_list_regionpos, f_getregionpos},
     {"getregtype",	0, 1, FEARG_1,	    arg1_string,
 			ret_string,	    f_getregtype},
     {"getscriptinfo",	0, 1, 0,	    arg1_dict_any,
--- a/src/globals.h
+++ b/src/globals.h
@@ -519,31 +519,37 @@ EXTERN int	garbage_collect_at_exit INIT(
 #define t_list_list_any		(static_types[70])
 #define t_const_list_list_any	(static_types[71])
 
-#define t_list_list_string	(static_types[72])
-#define t_const_list_list_string (static_types[73])
+#define t_list_list_number	(static_types[72])
+#define t_const_list_list_number (static_types[73])
 
-#define t_dict_bool		(static_types[74])
-#define t_const_dict_bool	(static_types[75])
+#define t_list_list_string	(static_types[74])
+#define t_const_list_list_string (static_types[75])
 
-#define t_dict_number		(static_types[76])
-#define t_const_dict_number	(static_types[77])
+#define t_list_list_list_number	(static_types[76])
+#define t_const_list_list_list_number (static_types[77])
 
-#define t_dict_string		(static_types[78])
-#define t_const_dict_string	(static_types[79])
+#define t_dict_bool		(static_types[78])
+#define t_const_dict_bool	(static_types[79])
+
+#define t_dict_number		(static_types[80])
+#define t_const_dict_number	(static_types[81])
 
-#define t_super			(static_types[80])
-#define t_const_super		(static_types[81])
+#define t_dict_string		(static_types[82])
+#define t_const_dict_string	(static_types[83])
 
-#define t_object		(static_types[82])
-#define t_const_object		(static_types[83])
+#define t_super			(static_types[84])
+#define t_const_super		(static_types[85])
 
-#define t_class			(static_types[84])
-#define t_const_class		(static_types[85])
+#define t_object		(static_types[86])
+#define t_const_object		(static_types[87])
 
-#define t_typealias		(static_types[86])
-#define t_const_typealias	(static_types[87])
+#define t_class			(static_types[88])
+#define t_const_class		(static_types[89])
 
-EXTERN type_T static_types[88]
+#define t_typealias		(static_types[90])
+#define t_const_typealias	(static_types[91])
+
+EXTERN type_T static_types[92]
 #ifdef DO_INIT
 = {
     // 0: t_unknown
@@ -690,35 +696,43 @@ EXTERN type_T static_types[88]
     {VAR_LIST, 0, 0, TTFLAG_STATIC, &t_list_any, NULL, NULL},
     {VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_list_any, NULL, NULL},
 
-    // 72: t_list_list_string
+    // 74: t_list_list_number
+    {VAR_LIST, 0, 0, TTFLAG_STATIC, &t_list_number, NULL, NULL},
+    {VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_list_number, NULL, NULL},
+
+    // 74: t_list_list_string
     {VAR_LIST, 0, 0, TTFLAG_STATIC, &t_list_string, NULL, NULL},
     {VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_list_string, NULL, NULL},
 
-    // 74: t_dict_bool
+    // 76: t_list_list_list_number
+    {VAR_LIST, 0, 0, TTFLAG_STATIC, &t_list_list_number, NULL, NULL},
+    {VAR_LIST, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_list_list_number, NULL, NULL},
+
+    // 78: t_dict_bool
     {VAR_DICT, 0, 0, TTFLAG_STATIC, &t_bool, NULL, NULL},
     {VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_bool, NULL, NULL},
 
-    // 76: t_dict_number
+    // 80: t_dict_number
     {VAR_DICT, 0, 0, TTFLAG_STATIC, &t_number, NULL, NULL},
     {VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_number, NULL, NULL},
 
-    // 78: t_dict_string
+    // 82: t_dict_string
     {VAR_DICT, 0, 0, TTFLAG_STATIC, &t_string, NULL, NULL},
     {VAR_DICT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_string, NULL, NULL},
 
-    // 80: t_super (VAR_CLASS with tt_member set to &t_bool
+    // 84: t_super (VAR_CLASS with tt_member set to &t_bool
     {VAR_CLASS, 0, 0, TTFLAG_STATIC, &t_bool, NULL, NULL},
     {VAR_CLASS, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, &t_bool, NULL, NULL},
 
-    // 82: t_object
+    // 86: t_object
     {VAR_OBJECT, 0, 0, TTFLAG_STATIC, NULL, NULL, NULL},
     {VAR_OBJECT, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL, NULL},
 
-    // 84: t_class
+    // 88: t_class
     {VAR_CLASS, 0, 0, TTFLAG_STATIC, NULL, NULL, NULL},
     {VAR_CLASS, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL, NULL},
 
-    // 86: t_typealias
+    // 90: t_typealias
     {VAR_TYPEALIAS, 0, 0, TTFLAG_STATIC, NULL, NULL, NULL},
     {VAR_TYPEALIAS, 0, 0, TTFLAG_STATIC|TTFLAG_CONST, NULL, NULL, NULL},
 }
--- a/src/testdir/test_vim9_builtin.vim
+++ b/src/testdir/test_vim9_builtin.vim
@@ -1969,6 +1969,17 @@ def Test_getreginfo()
   getreginfo('').regcontents->assert_equal(['D1E2F3'])
 enddef
 
+def Test_getregionpos()
+  var lines =<< trim END
+    cursor(1, 1)
+    var pos = getregionpos(getpos('.'), getpos('$'))
+    for p in pos
+      assert_equal(bufnr('%'), p[0][0])
+    endfor
+  END
+  v9.CheckSourceDefSuccess(lines)
+enddef
+
 def Test_getregtype()
   var lines = ['aaa', 'bbb', 'ccc']
   setreg('a', lines)
--- 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 */
 /**/
+    590,
+/**/
     589,
 /**/
     588,