To: vim_dev@googlegroups.com Subject: Patch 8.2.2263 Fcc: outbox From: Bram Moolenaar Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ------------ Patch 8.2.2263 Problem: Vim9: compilation error with try-catch in skipped block. Solution: Do not bail out when generate_instr() returns NULL. (closes #7584) Files: src/vim9compile.c, src/testdir/test_vim9_script.vim *** ../vim-8.2.2262/src/vim9compile.c 2021-01-01 14:49:11.908956386 +0100 --- src/vim9compile.c 2021-01-01 16:04:51.228065012 +0100 *************** *** 6916,6926 **** if (try_scope == NULL) return NULL; ! // "catch" is set when the first ":catch" is found. ! // "finally" is set when ":finally" or ":endtry" is found ! try_scope->se_u.se_try.ts_try_label = instr->ga_len; ! if (generate_instr(cctx, ISN_TRY) == NULL) ! return NULL; // scope for the try block itself scope = new_scope(cctx, BLOCK_SCOPE); --- 6916,6929 ---- if (try_scope == NULL) return NULL; ! if (cctx->ctx_skip != SKIP_YES) ! { ! // "catch" is set when the first ":catch" is found. ! // "finally" is set when ":finally" or ":endtry" is found ! try_scope->se_u.se_try.ts_try_label = instr->ga_len; ! if (generate_instr(cctx, ISN_TRY) == NULL) ! return NULL; ! } // scope for the try block itself scope = new_scope(cctx, BLOCK_SCOPE); *************** *** 6959,6978 **** return NULL; } ! // Jump from end of previous block to :finally or :endtry ! if (compile_jump_to_end(&scope->se_u.se_try.ts_end_label, JUMP_ALWAYS, cctx) == FAIL) ! return NULL; ! // End :try or :catch scope: set value in ISN_TRY instruction ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_try_label; ! if (isn->isn_arg.try.try_catch == 0) ! isn->isn_arg.try.try_catch = instr->ga_len; ! if (scope->se_u.se_try.ts_catch_label != 0) ! { ! // Previous catch without match jumps here ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_catch_label; ! isn->isn_arg.jump.jump_where = instr->ga_len; } p = skipwhite(arg); --- 6962,6984 ---- return NULL; } ! if (cctx->ctx_skip != SKIP_YES) ! { ! // Jump from end of previous block to :finally or :endtry ! if (compile_jump_to_end(&scope->se_u.se_try.ts_end_label, JUMP_ALWAYS, cctx) == FAIL) ! return NULL; ! // End :try or :catch scope: set value in ISN_TRY instruction ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_try_label; ! if (isn->isn_arg.try.try_catch == 0) ! isn->isn_arg.try.try_catch = instr->ga_len; ! if (scope->se_u.se_try.ts_catch_label != 0) ! { ! // Previous catch without match jumps here ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_catch_label; ! isn->isn_arg.jump.jump_where = instr->ga_len; ! } } p = skipwhite(arg); *************** *** 7019,7025 **** return NULL; } ! if (generate_instr(cctx, ISN_CATCH) == NULL) return NULL; if (new_scope(cctx, BLOCK_SCOPE) == NULL) --- 7025,7031 ---- return NULL; } ! if (cctx->ctx_skip != SKIP_YES && generate_instr(cctx, ISN_CATCH) == NULL) return NULL; if (new_scope(cctx, BLOCK_SCOPE) == NULL) *************** *** 7097,7129 **** return NULL; } ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_try_label; ! if (isn->isn_arg.try.try_catch == 0 && isn->isn_arg.try.try_finally == 0) { ! emsg(_(e_missing_catch_or_finally)); ! return NULL; ! } ! // Fill in the "end" label in jumps at the end of the blocks, if not done ! // by ":finally". ! compile_fill_jump_to_end(&scope->se_u.se_try.ts_end_label, cctx); ! // End :catch or :finally scope: set value in ISN_TRY instruction ! if (isn->isn_arg.try.try_catch == 0) ! isn->isn_arg.try.try_catch = instr->ga_len; ! if (isn->isn_arg.try.try_finally == 0) ! isn->isn_arg.try.try_finally = instr->ga_len; ! ! if (scope->se_u.se_try.ts_catch_label != 0) ! { ! // Last catch without match jumps here ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_catch_label; ! isn->isn_arg.jump.jump_where = instr->ga_len; } compile_endblock(cctx); ! if (generate_instr(cctx, ISN_ENDTRY) == NULL) return NULL; return arg; } --- 7103,7139 ---- return NULL; } ! if (cctx->ctx_skip != SKIP_YES) { ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_try_label; ! if (isn->isn_arg.try.try_catch == 0 ! && isn->isn_arg.try.try_finally == 0) ! { ! emsg(_(e_missing_catch_or_finally)); ! return NULL; ! } ! // Fill in the "end" label in jumps at the end of the blocks, if not ! // done by ":finally". ! compile_fill_jump_to_end(&scope->se_u.se_try.ts_end_label, cctx); ! ! // End :catch or :finally scope: set value in ISN_TRY instruction ! if (isn->isn_arg.try.try_catch == 0) ! isn->isn_arg.try.try_catch = instr->ga_len; ! if (isn->isn_arg.try.try_finally == 0) ! isn->isn_arg.try.try_finally = instr->ga_len; ! if (scope->se_u.se_try.ts_catch_label != 0) ! { ! // Last catch without match jumps here ! isn = ((isn_T *)instr->ga_data) + scope->se_u.se_try.ts_catch_label; ! isn->isn_arg.jump.jump_where = instr->ga_len; ! } } compile_endblock(cctx); ! if (cctx->ctx_skip != SKIP_YES && generate_instr(cctx, ISN_ENDTRY) == NULL) return NULL; return arg; } *** ../vim-8.2.2262/src/testdir/test_vim9_script.vim 2020-12-31 21:28:43.423217932 +0100 --- src/testdir/test_vim9_script.vim 2021-01-01 16:09:43.118910921 +0100 *************** *** 361,366 **** --- 361,395 ---- endtry assert_equal(99, n) + var done = 'no' + if 0 + try | catch | endtry + else + done = 'yes' + endif + assert_equal('yes', done) + + done = 'no' + if 1 + done = 'yes' + else + try | catch | endtry + done = 'never' + endif + assert_equal('yes', done) + + if 1 + else + try | catch /pat/ | endtry + try | catch /pat/ + endtry + try + catch /pat/ | endtry + try + catch /pat/ + endtry + endif + try # string slice returns a string, not a number n = g:astring[3] *** ../vim-8.2.2262/src/version.c 2021-01-01 15:11:00.008727261 +0100 --- src/version.c 2021-01-01 15:59:30.649382341 +0100 *************** *** 752,753 **** --- 752,755 ---- { /* Add new patch number below this line */ + /**/ + 2263, /**/ -- hundred-and-one symptoms of being an internet addict: 75. You start wondering whether you could actually upgrade your brain with a Pentium Pro microprocessor 80. The upgrade works just fine. /// 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 ///