Skip to content

Commit 26a4484

Browse files
committed
patch 8.2.3395: Vim9: expression breakpoint not checked in :def function
Problem: Vim9: expression breakpoint not checked in :def function. Solution: Always compile a function for debugging if there is an expression breakpoint. (closes #8803)
1 parent 04626c2 commit 26a4484

File tree

8 files changed

+75
-5
lines changed

8 files changed

+75
-5
lines changed

src/debugger.c

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -518,6 +518,7 @@ static garray_T dbg_breakp = {0, 0, sizeof(struct debuggy), 4, NULL};
518518
#define BREAKP(idx) (((struct debuggy *)dbg_breakp.ga_data)[idx])
519519
#define DEBUGGY(gap, idx) (((struct debuggy *)gap->ga_data)[idx])
520520
static int last_breakp = 0; // nr of last defined breakpoint
521+
static int has_expr_breakpoint = FALSE;
521522

522523
#ifdef FEAT_PROFILE
523524
// Profiling uses file and func names similar to breakpoints.
@@ -691,6 +692,8 @@ ex_breakadd(exarg_T *eap)
691692
// DBG_EXPR
692693
DEBUGGY(gap, gap->ga_len++).dbg_nr = ++last_breakp;
693694
++debug_tick;
695+
if (gap == &dbg_breakp)
696+
has_expr_breakpoint = TRUE;
694697
}
695698
}
696699
}
@@ -707,6 +710,29 @@ ex_debuggreedy(exarg_T *eap)
707710
debug_greedy = FALSE;
708711
}
709712

713+
static void
714+
update_has_expr_breakpoint()
715+
{
716+
int i;
717+
718+
has_expr_breakpoint = FALSE;
719+
for (i = 0; i < dbg_breakp.ga_len; ++i)
720+
if (BREAKP(i).dbg_type == DBG_EXPR)
721+
{
722+
has_expr_breakpoint = TRUE;
723+
break;
724+
}
725+
}
726+
727+
/*
728+
* Return TRUE if there is any expression breakpoint.
729+
*/
730+
int
731+
debug_has_expr_breakpoint()
732+
{
733+
return has_expr_breakpoint;
734+
}
735+
710736
/*
711737
* ":breakdel" and ":profdel".
712738
*/
@@ -799,6 +825,8 @@ ex_breakdel(exarg_T *eap)
799825
// If all breakpoints were removed clear the array.
800826
if (gap->ga_len == 0)
801827
ga_clear(gap);
828+
if (gap == &dbg_breakp)
829+
update_has_expr_breakpoint();
802830
}
803831
}
804832

src/proto/debugger.pro

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ void dbg_check_breakpoint(exarg_T *eap);
66
int dbg_check_skipped(exarg_T *eap);
77
void ex_breakadd(exarg_T *eap);
88
void ex_debuggreedy(exarg_T *eap);
9+
int debug_has_expr_breakpoint(void);
910
void ex_breakdel(exarg_T *eap);
1011
void ex_breaklist(exarg_T *eap);
1112
linenr_T dbg_find_breakpoint(int file, char_u *fname, linenr_T after);

src/proto/vim9execute.pro

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ char_u *char_from_string(char_u *str, varnumber_T index);
55
char_u *string_slice(char_u *str, varnumber_T first, varnumber_T last, int exclusive);
66
int fill_partial_and_closure(partial_T *pt, ufunc_T *ufunc, ectx_T *ectx);
77
typval_T *lookup_debug_var(char_u *name);
8+
int may_break_in_function(ufunc_T *ufunc);
89
int exe_typval_instr(typval_T *tv, typval_T *rettv);
910
char_u *exe_substitute_instr(void);
1011
int call_def_function(ufunc_T *ufunc, int argc_arg, typval_T *argv, partial_T *partial, typval_T *rettv);

src/testdir/test_debugger.vim

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -932,6 +932,27 @@ func Test_Backtrace_DefFunction()
932932
call delete('Xtest2.vim')
933933
endfunc
934934

935+
func Test_DefFunction_expr()
936+
CheckCWD
937+
let file3 =<< trim END
938+
vim9script
939+
g:someVar = "foo"
940+
def g:ChangeVar()
941+
g:someVar = "bar"
942+
echo "changed"
943+
enddef
944+
defcompile
945+
END
946+
call writefile(file3, 'Xtest3.vim')
947+
let buf = RunVimInTerminal('-S Xtest3.vim', {})
948+
949+
call RunDbgCmd(buf, ':breakadd expr g:someVar')
950+
call RunDbgCmd(buf, ':call g:ChangeVar()', ['Oldval = "''foo''"', 'Newval = "''bar''"', 'function ChangeVar', 'line 2: echo "changed"'])
951+
952+
call StopVimInTerminal(buf)
953+
call delete('Xtest3.vim')
954+
endfunc
955+
935956
func Test_debug_def_and_legacy_function()
936957
CheckCWD
937958
let file =<< trim END

src/version.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -755,6 +755,8 @@ static char *(features[]) =
755755

756756
static int included_patches[] =
757757
{ /* Add new patch number below this line */
758+
/**/
759+
3395,
758760
/**/
759761
3394,
760762
/**/

src/vim.h

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1808,9 +1808,16 @@ typedef enum {
18081808

18091809
// Keep in sync with INSTRUCTIONS().
18101810
#ifdef FEAT_PROFILE
1811-
# define COMPILE_TYPE(ufunc) (debug_break_level > 0 || ufunc->uf_has_breakpoint ? CT_DEBUG : do_profiling == PROF_YES && (ufunc)->uf_profiling ? CT_PROFILE : CT_NONE)
1811+
# define COMPILE_TYPE(ufunc) (debug_break_level > 0 \
1812+
|| may_break_in_function(ufunc) \
1813+
? CT_DEBUG \
1814+
: do_profiling == PROF_YES && (ufunc)->uf_profiling \
1815+
? CT_PROFILE : CT_NONE)
18121816
#else
1813-
# define COMPILE_TYPE(ufunc) debug_break_level > 0 || ufunc->uf_has_breakpoint ? CT_DEBUG : CT_NONE
1817+
# define COMPILE_TYPE(ufunc) debug_break_level > 0 \
1818+
|| may_break_in_function(ufunc) \
1819+
? CT_DEBUG \
1820+
: CT_NONE
18141821
#endif
18151822

18161823
/*

src/vim9.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -513,14 +513,14 @@ extern garray_T def_functions;
513513
// Keep in sync with COMPILE_TYPE()
514514
#ifdef FEAT_PROFILE
515515
# define INSTRUCTIONS(dfunc) \
516-
(debug_break_level > 0 || dfunc->df_ufunc->uf_has_breakpoint \
516+
(debug_break_level > 0 || may_break_in_function(dfunc->df_ufunc) \
517517
? (dfunc)->df_instr_debug \
518518
: ((do_profiling == PROF_YES && (dfunc->df_ufunc)->uf_profiling) \
519519
? (dfunc)->df_instr_prof \
520520
: (dfunc)->df_instr))
521521
#else
522522
# define INSTRUCTIONS(dfunc) \
523-
(debug_break_level > 0 || dfunc->df_ufunc->uf_has_breakpoint \
523+
(debug_break_level > 0 || may_break_in_function(dfunc->df_ufunc) \
524524
? (dfunc)->df_instr_debug \
525525
: (dfunc)->df_instr)
526526
#endif

src/vim9execute.c

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1483,6 +1483,16 @@ lookup_debug_var(char_u *name)
14831483
return NULL;
14841484
}
14851485

1486+
/*
1487+
* Return TRUE if there might be a breakpoint in "ufunc", which is when a
1488+
* breakpoint was set in that function or when there is any expression.
1489+
*/
1490+
int
1491+
may_break_in_function(ufunc_T *ufunc)
1492+
{
1493+
return ufunc->uf_has_breakpoint || debug_has_expr_breakpoint();
1494+
}
1495+
14861496
static void
14871497
handle_debug(isn_T *iptr, ectx_T *ectx)
14881498
{
@@ -1498,7 +1508,7 @@ handle_debug(isn_T *iptr, ectx_T *ectx)
14981508
{
14991509
linenr_T breakpoint;
15001510

1501-
if (!ufunc->uf_has_breakpoint)
1511+
if (!may_break_in_function(ufunc))
15021512
return;
15031513

15041514
// check for the next breakpoint if needed

0 commit comments

Comments
 (0)