summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--runtime/pack/dist/opt/termdebug/plugin/termdebug.vim421
-rw-r--r--src/testdir/test_termdebug.vim11
-rw-r--r--src/version.c2
3 files changed, 252 insertions, 182 deletions
diff --git a/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim b/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim
index 0a40164b7a..15d0397198 100644
--- a/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim
+++ b/runtime/pack/dist/opt/termdebug/plugin/termdebug.vim
@@ -4,7 +4,7 @@ vim9script
# Author: Bram Moolenaar
# Copyright: Vim license applies, see ":help license"
-# Last Change: 2024 Jun 03
+# Last Change: 2024 Jun 13
# Converted to Vim9: Ubaldo Tiberi <ubaldo.tiberi@gmail.com>
# WORK IN PROGRESS - The basics works stable, more to come
@@ -38,44 +38,56 @@ vim9script
# The communication with gdb uses GDB/MI. See:
# https://sourceware.org/gdb/current/onlinedocs/gdb/GDB_002fMI.html
-# In case this gets sourced twice.
+def Echoerr(msg: string)
+ echohl ErrorMsg | echom $'[termdebug] {msg}' | echohl None
+enddef
+
+
+# Variables to keep their status among multiple instances of Termdebug
+# Avoid to source the script twice.
if exists('g:termdebug_loaded')
- finish
+ Echoerr('Termdebug already loaded.')
+ finish
endif
g:termdebug_loaded = true
-var way = 'terminal'
-var err = 'no errors'
+# Script variables declaration. These variables are re-initialized at every
+# Termdebug instance
+var way: string
+var err: string
-var pc_id = 12
-var asm_id = 13
-var break_id = 14 # breakpoint number is added to this
-var stopped = 1
-var running = 0
+var pc_id: number
+var asm_id: number
+var break_id: number
+var stopped: bool
+var running: bool
-var parsing_disasm_msg = 0
-var asm_lines = []
-var asm_addr = ''
+var parsing_disasm_msg: number
+var asm_lines: list<string>
+var asm_addr: string
# These shall be constants but cannot be initialized here
# They indicate the buffer numbers of the main buffers used
-var gdbbuf = 0
-var varbuf = 0
-var asmbuf = 0
-var promptbuf = 0
+var gdbbufnr: number
+var gdbbufname: string
+var varbufnr: number
+var varbufname: string
+var asmbufnr: number
+var asmbufname: string
+var promptbuf: number
# This is for the "debugged program" thing
-var ptybuf = 0
-var commbuf = 0
+var ptybufnr: number
+var commbufnr: number
-var gdbjob = null_job
-var gdb_channel = null_channel
+var gdbjob: job
+var gdb_channel: channel
# These changes because they relate to windows
-var pid = 0
-var gdbwin = 0
-var varwin = 0
-var asmwin = 0
-var ptywin = 0
-var sourcewin = 0
+var pid: number
+var gdbwin: number
+var varwin: number
+var asmwin: number
+var ptywin: number
+var sourcewin: number
# Contains breakpoints that have been placed, key is a string with the GDB
# breakpoint number.
@@ -84,52 +96,112 @@ var sourcewin = 0
# For a breakpoint "123.4" the id is "123" and subid is "4".
# Example, when breakpoint "44", "123", "123.1" and "123.2" exist:
# {'44': {'0': entry}, '123': {'0': entry, '1': entry, '2': entry}}
-var breakpoints = {}
+var breakpoints: dict<any>
# Contains breakpoints by file/lnum. The key is "fname:lnum".
# Each entry is a list of breakpoint IDs at that position.
-var breakpoint_locations = {}
-var BreakpointSigns: list<string> = []
-
+var breakpoint_locations: dict<any>
+var BreakpointSigns: list<string>
-var evalFromBalloonExpr = 0
-var evalFromBalloonExprResult = ''
-var ignoreEvalError = 0
-var evalexpr = ''
+var evalFromBalloonExpr: bool
+var evalFromBalloonExprResult: string
+var ignoreEvalError: bool
+var evalexpr: string
# Remember the old value of 'signcolumn' for each buffer that it's set in, so
# that we can restore the value for all buffers.
-var signcolumn_buflist = [bufnr()]
-var save_columns = 0
+var signcolumn_buflist: list<number>
+var save_columns: number
-var allleft = 0
+var allleft: bool
# This was s:vertical but I cannot use vertical as variable name
-var vvertical = 0
-
-var winbar_winids = []
-var plus_map_saved = {}
-var minus_map_saved = {}
-var k_map_saved = {}
-var saved_mousemodel = null_string
-
-
-# Need either the +terminal feature or +channel and the prompt buffer.
-# The terminal feature does not work with gdb on win32.
-if has('terminal') && !has('win32')
- way = 'terminal'
-elseif has('channel') && exists('*prompt_setprompt')
- way = 'prompt'
-else
- if has('terminal')
- err = 'Cannot debug, missing prompt buffer support'
+var vvertical: bool
+
+var winbar_winids: list<number>
+
+var saved_mousemodel: string
+
+var k_map_saved: dict<any>
+var plus_map_saved: dict<any>
+var minus_map_saved: dict<any>
+
+
+def InitScriptVariables()
+ if exists('g:termdebug_config') && has_key(g:termdebug_config, 'use_prompt')
+ way = g:termdebug_config['use_prompt'] ? 'prompt' : 'terminal'
+ elseif exists('g:termdebug_use_prompt')
+ way = g:termdebug_use_prompt
+ elseif has('terminal') && !has('win32')
+ way = 'terminal'
else
- err = 'Cannot debug, +channel feature is not supported'
+ way = 'prompt'
endif
- command -nargs=* -complete=file -bang Termdebug echoerr err
- command -nargs=+ -complete=file -bang TermdebugCommand echoerr err
- finish
-endif
+ err = ''
+
+ pc_id = 12
+ asm_id = 13
+ break_id = 14 # breakpoint number is added to this
+ stopped = true
+ running = false
+
+ parsing_disasm_msg = 0
+ asm_lines = []
+ asm_addr = ''
+
+ # They indicate the buffer numbers of the main buffers used
+ gdbbufnr = 0
+ gdbbufname = 'gdb'
+ varbufnr = 0
+ varbufname = 'Termdebug-variables-listing'
+ asmbufnr = 0
+ asmbufname = 'Termdebug-asm-listing'
+ promptbuf = 0
+ # This is for the "debugged program" thing
+ ptybufnr = 0
+ commbufnr = 0
+
+ gdbjob = null_job
+ gdb_channel = null_channel
+ # These changes because they relate to windows
+ pid = 0
+ gdbwin = 0
+ varwin = 0
+ asmwin = 0
+ ptywin = 0
+ sourcewin = 0
+
+ # Contains breakpoints that have been placed, key is a string with the GDB
+ # breakpoint number.
+ # Each entry is a dict, containing the sub-breakpoints. Key is the subid.
+ # For a breakpoint that is just a number the subid is zero.
+ # For a breakpoint "123.4" the id is "123" and subid is "4".
+ # Example, when breakpoint "44", "123", "123.1" and "123.2" exist:
+ # {'44': {'0': entry}, '123': {'0': entry, '1': entry, '2': entry}}
+ breakpoints = {}
+
+ # Contains breakpoints by file/lnum. The key is "fname:lnum".
+ # Each entry is a list of breakpoint IDs at that position.
+ breakpoint_locations = {}
+ BreakpointSigns = []
+
+ evalFromBalloonExpr = false
+ evalFromBalloonExprResult = ''
+ ignoreEvalError = false
+ evalexpr = ''
+ # Remember the old value of 'signcolumn' for each buffer that it's set in, so
+ # that we can restore the value for all buffers.
+ signcolumn_buflist = [bufnr()]
+ save_columns = 0
+ winbar_winids = []
+ k_map_saved = {}
+ plus_map_saved = {}
+ minus_map_saved = {}
+
+ if has('menu')
+ saved_mousemodel = null_string
+ endif
+enddef
# The command that starts debugging, e.g. ":Termdebug vim".
# To end type "quit" in the gdb window.
command -nargs=* -complete=file -bang Termdebug StartDebug(<bang>0, <f-args>)
@@ -182,11 +254,8 @@ def GetCommand(): list<string>
return type(cmd) == v:t_list ? copy(cmd) : [cmd]
enddef
-def Echoerr(msg: string)
- echohl ErrorMsg | echom $'[termdebug] {msg}' | echohl None
-enddef
-
def StartDebug(bang: bool, ...gdb_args: list<string>)
+ InitScriptVariables()
# First argument is the command to debug, second core file or process ID.
StartDebug_internal({gdb_args: gdb_args, bang: bang})
enddef
@@ -227,24 +296,11 @@ def StartDebug_internal(dict: dict<any>)
&columns = wide
# If we make the Vim window wider, use the whole left half for the debug
# windows.
- allleft = 1
+ allleft = true
endif
- vvertical = 1
- else
- vvertical = 0
- endif
-
- # Override using a terminal window by setting g:termdebug_use_prompt to 1.
- var use_prompt = 0
- if exists('g:termdebug_config')
- use_prompt = get(g:termdebug_config, 'use_prompt', 0)
- elseif exists('g:termdebug_use_prompt')
- use_prompt = g:termdebug_use_prompt
- endif
- if has('terminal') && !has('win32') && !use_prompt
- way = 'terminal'
+ vvertical = true
else
- way = 'prompt'
+ vvertical = false
endif
if way == 'prompt'
@@ -272,45 +328,42 @@ enddef
# Use when debugger didn't start or ended.
def CloseBuffers()
- exe $'bwipe! {ptybuf}'
- exe $'bwipe! {commbuf}'
- if asmbuf > 0 && bufexists(asmbuf)
- exe $'bwipe! {asmbuf}'
+ exe $'bwipe! {ptybufnr}'
+ exe $'bwipe! {commbufnr}'
+ if asmbufnr > 0 && bufexists(asmbufnr)
+ exe $'bwipe! {asmbufnr}'
endif
- if varbuf > 0 && bufexists(varbuf)
- exe $'bwipe! {varbuf}'
+ if varbufnr > 0 && bufexists(varbufnr)
+ exe $'bwipe! {varbufnr}'
endif
running = 0
gdbwin = 0
enddef
# IsGdbRunning(): bool may be a better name?
-def CheckGdbRunning(): string
- var gdbproc = term_getjob(gdbbuf)
- var gdbproc_status = 'unknown'
- if type(gdbproc) == v:t_job
- gdbproc_status = job_status(gdbproc)
- endif
- if gdbproc == v:null || gdbproc_status !=# 'run'
+def IsGdbStarted(): bool
+ var gdbproc_status = job_status(term_getjob(gdbbufnr))
+ if gdbproc_status !=# 'run'
var cmd_name = string(GetCommand()[0])
Echoerr($'{cmd_name} exited unexpectedly')
CloseBuffers()
- return ''
+ return false
endif
- return 'ok'
+ return true
enddef
# Open a terminal window without a job, to run the debugged program in.
def StartDebug_term(dict: dict<any>)
- ptybuf = term_start('NONE', {
+ ptybufnr = term_start('NONE', {
term_name: 'debugged program',
vertical: vvertical})
- if ptybuf == 0
+ if ptybufnr == 0
Echoerr('Failed to open the program terminal window')
return
endif
- var pty = job_info(term_getjob(ptybuf))['tty_out']
+ var pty = job_info(term_getjob(ptybufnr))['tty_out']
ptywin = win_getid()
+
if vvertical
# Assuming the source code window will get a signcolumn, use two more
# columns for that, thus one less for the terminal window.
@@ -322,23 +375,26 @@ def StartDebug_term(dict: dict<any>)
endif
# Create a hidden terminal window to communicate with gdb
- commbuf = term_start('NONE', {
+ commbufnr = term_start('NONE', {
term_name: 'gdb communication',
out_cb: function('CommOutput'),
hidden: 1
})
- if commbuf == 0
+ if commbufnr == 0
Echoerr('Failed to open the communication terminal window')
- exe $'bwipe! {ptybuf}'
+ exe $'bwipe! {ptybufnr}'
return
endif
- var commpty = job_info(term_getjob(commbuf))['tty_out']
+ var commpty = job_info(term_getjob(commbufnr))['tty_out']
+ # Start the gdb buffer
var gdb_args = get(dict, 'gdb_args', [])
var proc_args = get(dict, 'proc_args', [])
var gdb_cmd = GetCommand()
+ gdbbufname = gdb_cmd[0]
+
if exists('g:termdebug_config') && has_key(g:termdebug_config, 'command_add_args')
gdb_cmd = g:termdebug_config.command_add_args(gdb_cmd, pty)
else
@@ -365,11 +421,11 @@ def StartDebug_term(dict: dict<any>)
gdb_cmd += gdb_args
ch_log($'executing "{join(gdb_cmd)}"')
- gdbbuf = term_start(gdb_cmd, {
- term_name: 'gdb',
- term_finish: 'close',
- })
- if gdbbuf == 0
+ gdbbufnr = term_start(gdb_cmd, {
+ term_name: gdbbufname,
+ term_finish: 'close',
+ })
+ if gdbbufnr == 0
Echoerr('Failed to open the gdb terminal window')
CloseBuffers()
return
@@ -380,14 +436,14 @@ def StartDebug_term(dict: dict<any>)
var counter = 0
var counter_max = 300
var success = false
- while success == false && counter < counter_max
- if CheckGdbRunning() != 'ok'
- # Failure. If NOK just return.
+ while !success && counter < counter_max
+ if !IsGdbStarted()
+ CloseBuffers()
return
endif
for lnum in range(1, 200)
- if term_getline(gdbbuf, lnum) =~ 'startupdone'
+ if term_getline(gdbbufnr, lnum) =~ 'startupdone'
success = true
endif
endfor
@@ -397,7 +453,7 @@ def StartDebug_term(dict: dict<any>)
sleep 10m
endwhile
- if success == false
+ if !success
Echoerr('Failed to startup the gdb program.')
CloseBuffers()
return
@@ -406,30 +462,30 @@ def StartDebug_term(dict: dict<any>)
# ---- gdb started. Next, let's set the MI interface. ---
# Set arguments to be run.
if len(proc_args)
- term_sendkeys(gdbbuf, $"server set args {join(proc_args)}\r")
+ term_sendkeys(gdbbufnr, $"server set args {join(proc_args)}\r")
endif
# Connect gdb to the communication pty, using the GDB/MI interface.
# Prefix "server" to avoid adding this to the history.
- term_sendkeys(gdbbuf, $"server new-ui mi {commpty}\r")
+ term_sendkeys(gdbbufnr, $"server new-ui mi {commpty}\r")
# Wait for the response to show up, users may not notice the error and wonder
# why the debugger doesn't work.
counter = 0
counter_max = 300
success = false
- while success == false && counter < counter_max
- if CheckGdbRunning() != 'ok'
+ while !success && counter < counter_max
+ if !IsGdbStarted()
return
endif
var response = ''
for lnum in range(1, 200)
- var line1 = term_getline(gdbbuf, lnum)
- var line2 = term_getline(gdbbuf, lnum + 1)
+ var line1 = term_getline(gdbbufnr, lnum)
+ var line2 = term_getline(gdbbufnr, lnum + 1)
if line1 =~ 'new-ui mi '
# response can be in the same line or the next line
- response = line1 .. line2
+ response = $"{line1}{line2}"
if response =~ 'Undefined command'
Echoerr('Sorry, your gdb is too old, gdb 7.12 is required')
# CHECKME: possibly send a "server show version" here
@@ -452,12 +508,12 @@ def StartDebug_term(dict: dict<any>)
sleep 10m
endwhile
- if success == false
+ if !success
Echoerr('Cannot check if your gdb works, continuing anyway')
return
endif
- job_setoptions(term_getjob(gdbbuf), {exit_cb: function('EndTermDebug')})
+ job_setoptions(term_getjob(gdbbufnr), {exit_cb: function('EndTermDebug')})
# Set the filetype, this can be used to add mappings.
set filetype=termdebug
@@ -531,23 +587,24 @@ def StartDebug_prompt(dict: dict<any>)
set modified
gdb_channel = job_getchannel(gdbjob)
- ptybuf = 0
+ ptybufnr = 0
if has('win32')
# MS-Windows: run in a new console window for maximum compatibility
SendCommand('set new-console on')
elseif has('terminal')
# Unix: Run the debugged program in a terminal window. Open it below the
# gdb window.
- belowright ptybuf = term_start('NONE', {
+ belowright ptybufnr = term_start('NONE', {
term_name: 'debugged program',
+ vertical: vvertical
})
- if ptybuf == 0
+ if ptybufnr == 0
Echoerr('Failed to open the program terminal window')
job_stop(gdbjob)
return
endif
ptywin = win_getid()
- var pty = job_info(term_getjob(ptybuf))['tty_out']
+ var pty = job_info(term_getjob(ptybufnr))['tty_out']
SendCommand($'tty {pty}')
# Since GDB runs in a prompt window, the environment has not been set to
@@ -615,7 +672,7 @@ def SendCommand(cmd: string)
if way == 'prompt'
ch_sendraw(gdb_channel, $"{cmd}\n")
else
- term_sendkeys(commbuf, $"{cmd}\r")
+ term_sendkeys(commbufnr, $"{cmd}\r")
endif
enddef
@@ -652,7 +709,7 @@ def TermDebugSendCommand(cmd: string)
sleep 10m
endif
# TODO: should we prepend CTRL-U to clear the command?
- term_sendkeys(gdbbuf, $"{cmd}\r")
+ term_sendkeys(gdbbufnr, $"{cmd}\r")
if do_continue
ContinueCommand()
endif
@@ -665,7 +722,7 @@ enddef
def SendResumingCommand(cmd: string)
if stopped
# reset stopped here, it may take a bit of time before we get a response
- stopped = 0
+ stopped = false
ch_log('assume that program is running after this command')
SendCommand(cmd)
else
@@ -715,9 +772,9 @@ def GdbOutCallback(channel: channel, text: string)
var decoded_text = ''
if text =~ '^\^error,msg='
decoded_text = DecodeMessage(text[11 : ], false)
- if exists('evalexpr') && decoded_text =~ 'A syntax error in expression, near\|No symbol .* in current context'
+ if !empty(evalexpr) && decoded_text =~ 'A syntax error in expression, near\|No symbol .* in current context'
# Silently drop evaluation errors.
- evalexpr = null_string
+ evalexpr = ''
return
endif
elseif text[0] == '~'
@@ -739,9 +796,9 @@ enddef
# Decode a message from gdb. "quotedText" starts with a ", return the text up
# to the next unescaped ", unescaping characters:
-# - remove line breaks (unless "literal" is v:true)
+# - remove line breaks (unless "literal" is true)
# - change \" to "
-# - change \\t to \t (unless "literal" is v:true)
+# - change \\t to \t (unless "literal" is true)
# - change \0xhh to \xhh (disabled for now)
# - change \ooo to octal
# - change \\ to \
@@ -751,19 +808,20 @@ def DecodeMessage(quotedText: string, literal: bool): string
return ''
endif
var msg = quotedText
- \ ->substitute('^"\|[^\\]\zs".*', '', 'g')
- \ ->substitute('\\"', '"', 'g')
+ ->substitute('^"\|[^\\]\zs".*', '', 'g')
+ ->substitute('\\"', '"', 'g')
#\ multi-byte characters arrive in octal form
#\ NULL-values must be kept encoded as those break the string otherwise
- \ ->substitute('\\000', NullRepl, 'g')
- \ ->substitute('\\\(\o\o\o\)', (m) => nr2char(str2nr(m[1], 8)), 'g')
+ ->substitute('\\000', NullRepl, 'g')
+ ->substitute('\\\(\o\o\o\)', (m) => nr2char(str2nr(m[1], 8)), 'g')
+ # You could also use ->substitute('\\\\\(\o\o\o\)', '\=nr2char(str2nr(submatch(1), 8))', "g")
#\ Note: GDB docs also mention hex encodings - the translations below work
#\ but we keep them out for performance-reasons until we actually see
#\ those in mi-returns
#\ \ ->substitute('\\0x\(\x\x\)', {-> eval('"\x' .. submatch(1) .. '"')}, 'g')
#\ \ ->substitute('\\0x00', NullRepl, 'g')
- \ ->substitute('\\\\', '\', 'g')
- \ ->substitute(NullRepl, '\\000', 'g')
+ ->substitute('\\\\', '\', 'g')
+ ->substitute(NullRepl, '\\000', 'g')
if !literal
return msg
->substitute('\\t', "\t", 'g')
@@ -805,8 +863,8 @@ def EndTermDebug(job: any, status: any)
doauto <nomodeline> User TermdebugStopPre
endif
- if bufexists(commbuf)
- exe $'bwipe! {commbuf}'
+ if commbufnr > 0 && bufexists(commbufnr)
+ exe $'bwipe! {commbufnr}'
endif
gdbwin = 0
EndDebugCommon()
@@ -815,16 +873,16 @@ enddef
def EndDebugCommon()
var curwinid = win_getid()
- if bufexists(ptybuf)
- exe $'bwipe! {ptybuf}'
+ if ptybufnr > 0 && bufexists(ptybufnr)
+ exe $'bwipe! {ptybufnr}'
endif
- if bufexists(asmbuf)
- exe $'bwipe! {asmbuf}'
+ if asmbufnr > 0 && bufexists(asmbufnr)
+ exe $'bwipe! {asmbufnr}'
endif
- if bufexists(varbuf)
- exe $'bwipe! {varbuf}'
+ if varbufnr > 0 && bufexists(varbufnr)
+ exe $'bwipe! {varbufnr}'
endif
- running = 0
+ running = false
# Restore 'signcolumn' in all buffers for which it was set.
win_gotoid(sourcewin)
@@ -932,11 +990,11 @@ def HandleDisasmMsg(msg: string)
endif
elseif msg !~ '^&"disassemble'
var value = substitute(msg, '^\~\"[ ]*', '', '')
- value = substitute(value, '^=>[ ]*', '', '')
- value = substitute(value, '\\n\"\r$', '', '')
- value = substitute(value, '\\n\"$', '', '')
- value = substitute(value, '\r', '', '')
- value = substitute(value, '\\t', ' ', 'g')
+ ->substitute('^=>[ ]*', '', '')
+ ->substitute('\\n\"\r$', '', '')
+ ->substitute('\\n\"$', '', '')
+ ->substitute('\r', '', '')
+ ->substitute('\\t', ' ', 'g')
if value != '' || !empty(asm_lines)
add(asm_lines, value)
@@ -1248,7 +1306,7 @@ def Until(at: string)
if stopped
# reset stopped here, it may take a bit of time before we get a response
- stopped = 0
+ stopped = false
ch_log('assume that program is running after this command')
# Use the fname:lnum format
@@ -1379,8 +1437,8 @@ enddef
# :Evaluate - evaluate what is specified / under the cursor
def Evaluate(range: number, arg: string)
var expr = GetEvaluationExpression(range, arg)
- #echom $"expr: {expr}"
- ignoreEvalError = 0
+ echom $"expr: {expr}"
+ ignoreEvalError = false
SendEval(expr)
enddef
@@ -1435,21 +1493,20 @@ enddef
def HandleEvaluate(msg: string)
var value = msg
- \ ->substitute('.*value="\(.*\)"', '\1', '')
- \ ->substitute('\\"', '"', 'g')
- \ ->substitute('\\\\', '\\', 'g')
+ ->substitute('.*value="\(.*\)"', '\1', '')
+ ->substitute('\\"', '"', 'g')
+ ->substitute('\\\\', '\\', 'g')
#\ multi-byte characters arrive in octal form, replace everything but NULL values
- \ ->substitute('\\000', NullRepl, 'g')
- # \ ->substitute('\\\o\o\o', {-> eval('"' .. submatch(0) .. '"')}, 'g')
- \ ->substitute('\\\(\o\o\o\)', (m) => nr2char(str2nr(m[1], 8)), 'g')
+ ->substitute('\\000', NullRepl, 'g')
+ ->substitute('\\\(\o\o\o\)', (m) => nr2char(str2nr(m[1], 8)), 'g')
#\ Note: GDB docs also mention hex encodings - the translations below work
#\ but we keep them out for performance-reasons until we actually see
#\ those in mi-returns
#\ ->substitute('\\0x00', NullRep, 'g')
#\ ->substitute('\\0x\(\x\x\)', {-> eval('"\x' .. submatch(1) .. '"')}, 'g')
- \ ->substitute(NullRepl, '\\000', 'g')
+ ->substitute(NullRepl, '\\000', 'g')
if evalFromBalloonExpr
- if evalFromBalloonExprResult == ''
+ if empty(evalFromBalloonExprResult)
evalFromBalloonExprResult = $'{evalexpr}: {value}'
else
evalFromBalloonExprResult ..= $' = {value}'
@@ -1461,10 +1518,10 @@ def HandleEvaluate(msg: string)
if evalexpr[0] != '*' && value =~ '^0x' && value != '0x0' && value !~ '"$'
# Looks like a pointer, also display what it points to.
- ignoreEvalError = 1
+ ignoreEvalError = true
SendEval($'*{evalexpr}')
else
- evalFromBalloonExpr = 0
+ evalFromBalloonExpr = false
endif
enddef
@@ -1480,9 +1537,9 @@ def TermDebugBalloonExpr(): string
# mouse triggers a balloon.
return ''
endif
- evalFromBalloonExpr = 1
+ evalFromBalloonExpr = true
evalFromBalloonExprResult = ''
- ignoreEvalError = 1
+ ignoreEvalError = true
var expr = CleanupExpr(v:beval_text)
SendEval(expr)
return ''
@@ -1492,8 +1549,8 @@ enddef
def HandleError(msg: string)
if ignoreEvalError
# Result of SendEval() failed, ignore.
- ignoreEvalError = 0
- evalFromBalloonExpr = 0
+ ignoreEvalError = false
+ evalFromBalloonExpr = true
return
endif
var msgVal = substitute(msg, '.*msg="\(.*\)"', '\1', '')
@@ -1554,11 +1611,11 @@ def GotoAsmwinOrCreateIt()
setlocal signcolumn=no
setlocal modifiable
- if asmbuf > 0 && bufexists(asmbuf)
- exe $'buffer {asmbuf}'
+ if asmbufnr > 0 && bufexists(asmbufnr)
+ exe $'buffer {asmbufnr}'
elseif empty(glob('Termdebug-asm-listing'))
silent file Termdebug-asm-listing
- asmbuf = bufnr('Termdebug-asm-listing')
+ asmbufnr = bufnr('Termdebug-asm-listing')
else
Echoerr("You have a file/folder named 'Termdebug-asm-listing'. " ..
"Please exit and rename it because Termdebug may not work " ..
@@ -1628,11 +1685,11 @@ def GotoVariableswinOrCreateIt()
setlocal signcolumn=no
setlocal modifiable
- if varbuf > 0 && bufexists(varbuf)
- exe $'buffer {varbuf}'
+ if varbufnr > 0 && bufexists(varbufnr)
+ exe $'buffer {varbufnr}'
elseif empty(glob('Termdebug-variables-listing'))
silent file Termdebug-variables-listing
- varbuf = bufnr('Termdebug-variables-listing')
+ varbufnr = bufnr('Termdebug-variables-listing')
else
Echoerr("You have a file/folder named 'Termdebug-variables-listing'. " ..
"Please exit and rename it because Termdebug may not work " ..
@@ -1658,12 +1715,12 @@ def HandleCursor(msg: string)
ch_log('program stopped')
stopped = 1
if msg =~ '^\*stopped,reason="exited-normally"'
- running = 0
+ running = false
endif
elseif msg =~ '^\*running'
ch_log('program running')
- stopped = 0
- running = 1
+ stopped = false
+ running = true
endif
var fname = ''
@@ -1692,7 +1749,7 @@ def HandleCursor(msg: string)
endif
endif
- if running && stopped && bufwinnr('Termdebug-variables-listing') != -1
+ if running && stopped && bufwinnr(varbufname) != -1
SendCommand('-stack-list-variables 2')
endif
@@ -1709,13 +1766,13 @@ def HandleCursor(msg: string)
au SwapExists * echohl WarningMsg
| echo 'Warning: file is being edited elsewhere'
| echohl None
- | let v:swapchoice = 'o'
+ | v:swapchoice = 'o'
augroup END
if &modified
# TODO: find existing window
exe $'split {fnameescape(fname)}'
sourcewin = win_getid()
- call InstallWinbar(0)
+ InstallWinbar(0)
else
exe $'edit {fnameescape(fname)}'
endif
diff --git a/src/testdir/test_termdebug.vim b/src/testdir/test_termdebug.vim
index 62cafccb69..a9762df8a2 100644
--- a/src/testdir/test_termdebug.vim
+++ b/src/testdir/test_termdebug.vim
@@ -338,5 +338,16 @@ func Test_termdebug_bufnames()
unlet g:termdebug_config
endfunc
+function Test_termdebug_save_restore_variables()
+ let &mousemodel=''
+ Termdebug
+ call WaitForAssert({-> assert_equal(3, winnr('$'))})
+ call WaitForAssert({-> assert_match(&mousemodel, 'popup_setpos')})
+ wincmd t
+ quit!
+ call WaitForAssert({-> assert_equal(1, winnr('$'))})
+ call WaitForAssert({-> assert_true(empty(&mousemodel))})
+endfunction
+
" vim: shiftwidth=2 sts=2 expandtab
diff --git a/src/version.c b/src/version.c
index 1360d1cfc3..43a09d308b 100644
--- a/src/version.c
+++ b/src/version.c
@@ -705,6 +705,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
+ 482,
+/**/
481,
/**/
480,