patch 9.1.0080: unexpected error for modifying final list using +=

Problem:  unexpected error for modifying final list using += operator
          (Ernie Rael)
Solution: Allow List value modification of a final variable using +=
          operator
          (Yegappan Lakshmanan)

fixes: #13745
fixes: #13959
closes: #13962

Signed-off-by: Yegappan Lakshmanan <yegappan@yahoo.com>
Signed-off-by: Christian Brabandt <cb@256bit.org>
diff --git a/src/evalvars.c b/src/evalvars.c
index cbcf2a7..0a84afd 100644
--- a/src/evalvars.c
+++ b/src/evalvars.c
@@ -3977,7 +3977,14 @@
 	    if (check_typval_is_value(&di->di_tv) == FAIL)
 		goto failed;
 
-	    if (var_in_vim9script && (flags & ASSIGN_FOR_LOOP) == 0)
+	    // List and Blob types can be modified in-place using the "+="
+	    // compound operator.  For other types, this is not allowed.
+	    int type_inplace_modifiable =
+		(di->di_tv.v_type == VAR_LIST || di->di_tv.v_type == VAR_BLOB);
+
+	    if (var_in_vim9script && (flags & ASSIGN_FOR_LOOP) == 0
+		    && ((flags & ASSIGN_COMPOUND_OP) == 0
+			|| !type_inplace_modifiable))
 	    {
 		where_T where = WHERE_INIT;
 		svar_T  *sv = find_typval_in_script(&di->di_tv, sid, TRUE);
@@ -3998,7 +4005,11 @@
 		}
 	    }
 
-	    if ((flags & ASSIGN_FOR_LOOP) == 0
+	    // Modifying a final variable with a List value using the "+="
+	    // operator is allowed.  For other types, it is not allowed.
+	    if (((flags & ASSIGN_FOR_LOOP) == 0
+			&& ((flags & ASSIGN_COMPOUND_OP) == 0
+			    || !type_inplace_modifiable))
 				 ? var_check_permission(di, name) == FAIL
 				 : var_check_ro(di->di_flags, name, FALSE))
 		goto failed;