changeset 24448:faac16c365b6 v8.2.2764

patch 8.2.2764: memory leak when default function argument is allocated Commit: https://github.com/vim/vim/commit/b47bed2f7ada4dfae78f76f27473b83507e40315 Author: Bram Moolenaar <Bram@vim.org> Date: Wed Apr 14 17:06:43 2021 +0200 patch 8.2.2764: memory leak when default function argument is allocated Problem: Memory leak when default function argument is allocated. Solution: Free the expression result.
author Bram Moolenaar <Bram@vim.org>
date Wed, 14 Apr 2021 17:15:05 +0200
parents bbe84a902d14
children ca0d84e008e5
files src/testdir/test_functions.vim src/userfunc.c src/version.c
diffstat 3 files changed, 20 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- a/src/testdir/test_functions.vim
+++ b/src/testdir/test_functions.vim
@@ -1497,6 +1497,7 @@ endfunc
 
 func Test_balloon_show()
   CheckFeature balloon_eval
+
   " This won't do anything but must not crash either.
   call balloon_show('hi!')
   if !has('gui_running')
@@ -2650,4 +2651,12 @@ func Test_browsedir()
   call assert_fails('call browsedir("open", [])', 'E730:')
 endfunc
 
+func HasDefault(msg = 'msg')
+  return a:msg
+endfunc
+
+func Test_default_arg_value()
+  call assert_equal('msg', HasDefault())
+endfunc
+
 " vim: shiftwidth=2 sts=2 expandtab
--- a/src/userfunc.c
+++ b/src/userfunc.c
@@ -2188,6 +2188,8 @@ call_user_func(
     int		islambda = FALSE;
     char_u	numbuf[NUMBUFLEN];
     char_u	*name;
+    typval_T	*tv_to_free[MAX_FUNC_ARGS];
+    int		tv_to_free_len = 0;
 #ifdef FEAT_PROFILE
     profinfo_T	profile_info;
 #endif
@@ -2333,6 +2335,7 @@ call_user_func(
 	    if (isdefault)
 	    {
 		char_u	    *default_expr = NULL;
+
 		def_rettv.v_type = VAR_NUMBER;
 		def_rettv.vval.v_number = -1;
 
@@ -2374,6 +2377,10 @@ call_user_func(
 	v->di_tv = isdefault ? def_rettv : argvars[i];
 	v->di_tv.v_lock = VAR_FIXED;
 
+	if (isdefault)
+	    // Need to free this later, no matter where it's stored.
+	    tv_to_free[tv_to_free_len++] = &v->di_tv;
+
 	if (addlocal)
 	{
 	    // Named arguments should be accessed without the "a:" prefix in
@@ -2563,6 +2570,8 @@ call_user_func(
 
     did_emsg |= save_did_emsg;
     funcdepth_decrement();
+    for (i = 0; i < tv_to_free_len; ++i)
+	clear_tv(tv_to_free[i]);
     cleanup_function_call(fc);
 }
 
--- a/src/version.c
+++ b/src/version.c
@@ -751,6 +751,8 @@ static char *(features[]) =
 static int included_patches[] =
 {   /* Add new patch number below this line */
 /**/
+    2764,
+/**/
     2763,
 /**/
     2762,