To: vim_dev@googlegroups.com Subject: Patch 8.2.2435 Fcc: outbox From: Bram Moolenaar Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ------------ Patch 8.2.2435 Problem: setline() gives an error for some types. Solution: Allow any type, convert each item to a string. Files: runtime/doc/eval.txt, src/evalbuffer.c, src/typval.c, src/proto/typval.pro, src/debugger.c, src/vim9execute.c, src/testdir/test_bufline.vim, src/testdir/test_vim9_builtin.vim *** ../vim-8.2.2434/runtime/doc/eval.txt 2021-01-21 21:42:09.409150461 +0100 --- runtime/doc/eval.txt 2021-01-31 12:30:54.043296603 +0100 *************** *** 3099,3111 **** text line below line {lnum} in the current buffer. Otherwise append {text} as one text line below line {lnum} in the current buffer. {lnum} can be zero to insert a line before the first one. Returns 1 for failure ({lnum} out of range or out of memory), 0 for success. Example: > :let failed = append(line('$'), "# THE END") :let failed = append(0, ["Chapter 1", "the beginning"]) ! < Can also be used as a |method| after a List: > mylist->append(lnum) --- 3133,3147 ---- text line below line {lnum} in the current buffer. Otherwise append {text} as one text line below line {lnum} in the current buffer. + Any type of item is accepted and converted to a String. {lnum} can be zero to insert a line before the first one. Returns 1 for failure ({lnum} out of range or out of memory), 0 for success. Example: > :let failed = append(line('$'), "# THE END") :let failed = append(0, ["Chapter 1", "the beginning"]) ! < Can also be used as a |method| after a List, the base is ! passed as the second argument: > mylist->append(lnum) *************** *** 9324,9332 **** {lnum} is used like with |getline()|. When {lnum} is just below the last line the {text} will be added below the last line. ! If this succeeds, 0 is returned. If this fails (most likely ! because {lnum} is invalid) 1 is returned. Example: > :call setline(5, strftime("%c")) --- 9410,9420 ---- {lnum} is used like with |getline()|. When {lnum} is just below the last line the {text} will be added below the last line. + {text} can be any type or a List of any type, each item is + converted to a String. ! If this succeeds, FALSE is returned. If this fails (most likely ! because {lnum} is invalid) TRUE is returned. Example: > :call setline(5, strftime("%c")) *** ../vim-8.2.2434/src/evalbuffer.c 2021-01-03 19:51:01.396063220 +0100 --- src/evalbuffer.c 2021-01-31 12:39:42.533390495 +0100 *************** *** 128,134 **** } /* ! * Set line or list of lines in buffer "buf". */ static void set_buffer_lines( --- 128,135 ---- } /* ! * Set line or list of lines in buffer "buf" to "lines". ! * Any type is allowed and converted to a string. */ static void set_buffer_lines( *************** *** 187,193 **** li = l->lv_first; } else ! line = tv_get_string_chk(lines); // default result is zero == OK for (;;) --- 188,194 ---- li = l->lv_first; } else ! line = typval_tostring(lines, FALSE); // default result is zero == OK for (;;) *************** *** 197,203 **** // list argument, get next string if (li == NULL) break; ! line = tv_get_string_chk(&li->li_tv); li = li->li_next; } --- 198,205 ---- // list argument, get next string if (li == NULL) break; ! vim_free(line); ! line = typval_tostring(&li->li_tv, FALSE); li = li->li_next; } *************** *** 238,243 **** --- 240,246 ---- break; ++lnum; } + vim_free(line); if (added > 0) { *** ../vim-8.2.2434/src/typval.c 2021-01-30 23:05:08.102386261 +0100 --- src/typval.c 2021-01-31 12:39:04.777533166 +0100 *************** *** 927,934 **** return OK; } char_u * ! typval_tostring(typval_T *arg) { char_u *tofree; char_u numbuf[NUMBUFLEN]; --- 927,939 ---- return OK; } + /* + * Convert any type to a string, never give an error. + * When "quotes" is TRUE add quotes to a string. + * Returns an allocated string. + */ char_u * ! typval_tostring(typval_T *arg, int quotes) { char_u *tofree; char_u numbuf[NUMBUFLEN]; *************** *** 936,945 **** if (arg == NULL) return vim_strsave((char_u *)"(does not exist)"); ! ret = tv2string(arg, &tofree, numbuf, 0); ! // Make a copy if we have a value but it's not in allocated memory. ! if (ret != NULL && tofree == NULL) ! ret = vim_strsave(ret); return ret; } --- 941,958 ---- if (arg == NULL) return vim_strsave((char_u *)"(does not exist)"); ! if (!quotes && arg->v_type == VAR_STRING) ! { ! ret = vim_strsave(arg->vval.v_string == NULL ? (char_u *)"" ! : arg->vval.v_string); ! } ! else ! { ! ret = tv2string(arg, &tofree, numbuf, 0); ! // Make a copy if we have a value but it's not in allocated memory. ! if (ret != NULL && tofree == NULL) ! ret = vim_strsave(ret); ! } return ret; } *** ../vim-8.2.2434/src/proto/typval.pro 2021-01-30 23:05:08.102386261 +0100 --- src/proto/typval.pro 2021-01-31 12:40:28.265216674 +0100 *************** *** 21,27 **** int tv_check_lock(typval_T *tv, char_u *name, int use_gettext); void copy_tv(typval_T *from, typval_T *to); int typval_compare(typval_T *typ1, typval_T *typ2, exprtype_T type, int ic); ! char_u *typval_tostring(typval_T *arg); int tv_islocked(typval_T *tv); int tv_equal(typval_T *tv1, typval_T *tv2, int ic, int recursive); int eval_option(char_u **arg, typval_T *rettv, int evaluate); --- 21,27 ---- int tv_check_lock(typval_T *tv, char_u *name, int use_gettext); void copy_tv(typval_T *from, typval_T *to); int typval_compare(typval_T *typ1, typval_T *typ2, exprtype_T type, int ic); ! char_u *typval_tostring(typval_T *arg, int quotes); int tv_islocked(typval_T *tv); int tv_equal(typval_T *tv1, typval_T *tv2, int ic, int recursive); int eval_option(char_u **arg, typval_T *rettv, int evaluate); *** ../vim-8.2.2434/src/debugger.c 2021-01-24 12:53:30.780247041 +0100 --- src/debugger.c 2021-01-31 12:39:29.081441429 +0100 *************** *** 940,948 **** { if (bp->dbg_val == NULL) { ! debug_oldval = typval_tostring(NULL); bp->dbg_val = tv; ! debug_newval = typval_tostring(bp->dbg_val); line = TRUE; } else --- 940,948 ---- { if (bp->dbg_val == NULL) { ! debug_oldval = typval_tostring(NULL, TRUE); bp->dbg_val = tv; ! debug_newval = typval_tostring(bp->dbg_val, TRUE); line = TRUE; } else *************** *** 953,963 **** typval_T *v; line = TRUE; ! debug_oldval = typval_tostring(bp->dbg_val); // Need to evaluate again, typval_compare() overwrites // "tv". v = eval_expr(bp->dbg_name, NULL); ! debug_newval = typval_tostring(v); free_tv(bp->dbg_val); bp->dbg_val = v; } --- 953,963 ---- typval_T *v; line = TRUE; ! debug_oldval = typval_tostring(bp->dbg_val, TRUE); // Need to evaluate again, typval_compare() overwrites // "tv". v = eval_expr(bp->dbg_name, NULL); ! debug_newval = typval_tostring(v, TRUE); free_tv(bp->dbg_val); bp->dbg_val = v; } *************** *** 966,973 **** } else if (bp->dbg_val != NULL) { ! debug_oldval = typval_tostring(bp->dbg_val); ! debug_newval = typval_tostring(NULL); free_tv(bp->dbg_val); bp->dbg_val = NULL; line = TRUE; --- 966,973 ---- } else if (bp->dbg_val != NULL) { ! debug_oldval = typval_tostring(bp->dbg_val, TRUE); ! debug_newval = typval_tostring(NULL, TRUE); free_tv(bp->dbg_val); bp->dbg_val = NULL; line = TRUE; *** ../vim-8.2.2434/src/vim9execute.c 2021-01-25 21:01:45.077861178 +0100 --- src/vim9execute.c 2021-01-31 12:40:00.429322587 +0100 *************** *** 879,885 **** return FAIL; } } ! str = typval_tostring(tv); clear_tv(tv); tv->v_type = VAR_STRING; tv->vval.v_string = str; --- 879,885 ---- return FAIL; } } ! str = typval_tostring(tv, TRUE); clear_tv(tv); tv->v_type = VAR_STRING; tv->vval.v_string = str; *** ../vim-8.2.2434/src/testdir/test_bufline.vim 2020-08-12 18:50:31.871655841 +0200 --- src/testdir/test_bufline.vim 2021-01-31 12:57:06.877897821 +0100 *************** *** 5,10 **** --- 5,11 ---- source check.vim func Test_setbufline_getbufline() + " similar to Test_set_get_bufline() new let b = bufnr('%') hide *************** *** 38,43 **** --- 39,50 ---- call assert_equal(['e'], getbufline(b, 5)) call assert_equal([], getbufline(b, 6)) call assert_equal([], getbufline(b, 2, 1)) + + call setbufline(b, 2, [function('eval'), #{key: 123}, test_null_job()]) + call assert_equal(["function('eval')", + \ "{'key': 123}", + \ "no process"], + \ getbufline(b, 2, 4)) exe "bwipe! " . b endfunc *** ../vim-8.2.2434/src/testdir/test_vim9_builtin.vim 2021-01-30 23:05:08.102386261 +0100 --- src/testdir/test_vim9_builtin.vim 2021-01-31 13:03:29.993154241 +0100 *************** *** 767,772 **** --- 767,820 ---- bwipe! enddef + def Test_set_get_bufline() + # similar to Test_setbufline_getbufline() + var lines =<< trim END + new + var b = bufnr('%') + hide + assert_equal(0, setbufline(b, 1, ['foo', 'bar'])) + assert_equal(['foo'], getbufline(b, 1)) + assert_equal(['bar'], getbufline(b, '$')) + assert_equal(['foo', 'bar'], getbufline(b, 1, 2)) + exe "bd!" b + assert_equal([], getbufline(b, 1, 2)) + + split Xtest + setline(1, ['a', 'b', 'c']) + b = bufnr('%') + wincmd w + + assert_equal(1, setbufline(b, 5, 'x')) + assert_equal(1, setbufline(b, 5, ['x'])) + assert_equal(1, setbufline(b, 5, [])) + assert_equal(1, setbufline(b, 5, test_null_list())) + + assert_equal(1, 'x'->setbufline(bufnr('$') + 1, 1)) + assert_equal(1, ['x']->setbufline(bufnr('$') + 1, 1)) + assert_equal(1, []->setbufline(bufnr('$') + 1, 1)) + assert_equal(1, test_null_list()->setbufline(bufnr('$') + 1, 1)) + + assert_equal(['a', 'b', 'c'], getbufline(b, 1, '$')) + + assert_equal(0, setbufline(b, 4, ['d', 'e'])) + assert_equal(['c'], b->getbufline(3)) + assert_equal(['d'], getbufline(b, 4)) + assert_equal(['e'], getbufline(b, 5)) + assert_equal([], getbufline(b, 6)) + assert_equal([], getbufline(b, 2, 1)) + + setbufline(b, 2, [function('eval'), {key: 123}, test_null_job()]) + assert_equal(["function('eval')", + "{'key': 123}", + "no process"], + getbufline(b, 2, 4)) + + exe 'bwipe! ' .. b + END + CheckDefAndScriptSuccess(lines) + enddef + def Test_searchdecl() searchdecl('blah', true, true)->assert_equal(1) enddef *** ../vim-8.2.2434/src/version.c 2021-01-30 23:05:08.106386242 +0100 --- src/version.c 2021-01-31 12:22:47.876702322 +0100 *************** *** 752,753 **** --- 752,755 ---- { /* Add new patch number below this line */ + /**/ + 2435, /**/ -- "Time flies like an arrow". So I put an arrow on my desk, now awaiting one of these time flies showing up. /// Bram Moolenaar -- Bram@Moolenaar.net -- http://www.Moolenaar.net \\\ /// sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ \\\ \\\ an exciting new programming language -- http://www.Zimbu.org /// \\\ help me help AIDS victims -- http://ICCF-Holland.org ///