aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTom de Vries <tdevries@suse.de>2025-08-16 09:18:45 +0200
committerTom de Vries <tdevries@suse.de>2025-08-16 09:18:45 +0200
commit06a53717f7c5abfd87165f3e5c7f55f9a8f512a7 (patch)
treee1abb40dba62e9afc8b6675350eaefdc65d851c3
parent96265ee7fa3fcc3532a323cac74e3828df331114 (diff)
downloadbinutils-06a53717f7c5abfd87165f3e5c7f55f9a8f512a7.zip
binutils-06a53717f7c5abfd87165f3e5c7f55f9a8f512a7.tar.gz
binutils-06a53717f7c5abfd87165f3e5c7f55f9a8f512a7.tar.bz2
[gdb/testsuite] Handle unrecognized escape sequences better in tuiterm
When encountering an unrecognized escape sequence in Term::accept_gdb_output, a warning is issued: ... WARNING: timeout in accept_gdb_output ... and 0 is returned. Subsequent calls run into the same problem, so matching doesn't progress. Consequently, figuring out what the unrecognized escape sequence actually is depends on analyzing gdb's output as echoed into gdb.log. In the test added in this commit, gdb (well, a script gdb.tcl emulating gdb) outputs escape sequence "ESC ( B", which doesn't show up in recognizable form in gdb.log: ... foo^M^M ... and as mentioned the tuiterm screen only show: ... foo ... because matching doesn't progress beyond the unrecognized sequence. Fix this by rewriting accept_gdb_output to match gdb output using a phased approach that echoes unmatched escape sequences, giving us instead on the tuiterm screen: ... foo^[(B ... [ Since "ESC ( B" is now supported, the test-case has been updated to use "ESC ( % 5" instead. ] Tested on x86_64-linux. PR testsuite/33218 Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=33218
-rwxr-xr-xgdb/testsuite/gdb.tui/gdb.tcl20
-rw-r--r--gdb/testsuite/gdb.tui/tuiterm-2.exp28
-rw-r--r--gdb/testsuite/lib/tuiterm.exp83
3 files changed, 114 insertions, 17 deletions
diff --git a/gdb/testsuite/gdb.tui/gdb.tcl b/gdb/testsuite/gdb.tui/gdb.tcl
new file mode 100755
index 0000000..ca207ed
--- /dev/null
+++ b/gdb/testsuite/gdb.tui/gdb.tcl
@@ -0,0 +1,20 @@
+#!/usr/bin/env tclsh
+
+# Copyright 2025 Free Software Foundation, Inc.
+
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+puts "foo\033(%5"
+
+gets stdin
diff --git a/gdb/testsuite/gdb.tui/tuiterm-2.exp b/gdb/testsuite/gdb.tui/tuiterm-2.exp
index becb65a..a451834 100644
--- a/gdb/testsuite/gdb.tui/tuiterm-2.exp
+++ b/gdb/testsuite/gdb.tui/tuiterm-2.exp
@@ -151,3 +151,31 @@ with_override Term::accept_gdb_output test_accept_gdb_output {
}
}
}
+
+with_test_prefix "Unrecognized escape sequence" {
+ spawn $srcdir/$subdir/gdb.tcl
+ switch_gdb_spawn_id $spawn_id
+
+ Term::_setup 4 20
+
+ save_vars timeout {
+ set timeout 1
+
+ set line { 0 0 20 1 }
+
+ # Parse "foo".
+ gdb_assert { [Term::wait_for_region_contents \
+ {*}$line \
+ [string_to_regexp "foo"]] } \
+ "foo"
+
+ # Parse "\033(%5".
+ gdb_assert { ![Term::accept_gdb_output 0] } \
+ "fail to parse escape sequence"
+ gdb_assert { [Term::wait_for_region_contents \
+ {*}$line \
+ [string_to_regexp "^\[(%5"]] } \
+ "echoed escape sequence"
+ }
+ Term::dump_screen
+}
diff --git a/gdb/testsuite/lib/tuiterm.exp b/gdb/testsuite/lib/tuiterm.exp
index d622003..a084b43 100644
--- a/gdb/testsuite/lib/tuiterm.exp
+++ b/gdb/testsuite/lib/tuiterm.exp
@@ -999,31 +999,86 @@ proc Term::_setup {rows cols} {
# Accept some output from gdb and update the screen.
# Return 1 if successful, or 0 if a timeout occurred.
-proc Term::accept_gdb_output { } {
+proc Term::accept_gdb_output { {warn 1} } {
global expect_out
+
+ set ctls "\x07\x08\x0a\x0d"
+ set esc "\x1b"
+ set re_ctls "\[$ctls\]"
+ set re_others "\[^$esc$ctls\]"
+ set have_esc 0
gdb_expect {
- -re "^\[\x07\x08\x0a\x0d\]" {
+ -re ^$re_ctls {
scan $expect_out(0,string) %c val
set hexval [format "%02x" $val]
_log "wait_for: _ctl_0x${hexval}"
_ctl_0x${hexval}
}
- -re "^\x1b(\[0-9a-zA-Z\])" {
+ -re "^$esc" {
+ _log "wait_for: ESC"
+ set have_esc 1
+ }
+ -re "^$re_others+" {
+ _insert $expect_out(0,string)
+ }
+
+ timeout {
+ # Assume a timeout means we somehow missed the
+ # expected result, and carry on.
+ warning "timeout in accept_gdb_output"
+ dump_screen
+ return 0
+ }
+ }
+
+ if { !$have_esc } {
+ return 1
+ }
+
+ set re_csi [string_to_regexp "\["]
+ set have_csi 0
+ gdb_expect {
+ -re "^(\[0-9a-zA-Z\])" {
_log "wait_for: unsupported escape"
error "unsupported escape"
}
- -re "^\x1b(\[\\(\])(\[a-zA-Z\])" {
+ -re "^(\[\\(\])(\[a-zA-Z\])" {
scan $expect_out(1,string) %c val
set hexval [format "%02x" $val]
set cmd $expect_out(2,string)
eval _esc_0x${hexval}_$cmd
}
- -re "^\x1b(\[=>\])" {
+ -re "^(\[=>\])" {
scan $expect_out(1,string) %c val
set hexval [format "%02x" $val]
_esc_0x$hexval
}
- -re "^\x1b\\\[(\\??)(\[0-9;\]*)(\[a-zA-Z@`\])" {
+ -re "^$re_csi" {
+ _log "wait_for: CSI"
+ set have_csi 1
+ }
+
+ timeout {
+ # Assume a timeout means we somehow missed the
+ # expected result, and carry on.
+ if { $warn } {
+ warning "timeout in accept_gdb_output following ESC"
+ dump_screen
+ }
+ _insert "^\["
+ return 0
+ }
+ }
+
+ if { !$have_csi } {
+ return 1
+ }
+
+ set re_csi_prefix {[?]}
+ set re_csi_args {[0-9;]}
+ set re_csi_cmd {[a-zA-Z@`]}
+ gdb_expect {
+ -re "^($re_csi_prefix?)($re_csi_args*)($re_csi_cmd)" {
set prefix $expect_out(1,string)
set cmd $expect_out(3,string)
set params [split $expect_out(2,string) ";"]
@@ -1037,21 +1092,15 @@ proc Term::accept_gdb_output { } {
eval _csi_0x${hexval}_$cmd $params
}
}
- -re "^\x1b\\\[(\[0-9;\]*)(\[a-zA-Z@`\])" {
- set cmd $expect_out(2,string)
- set params [split $expect_out(1,string) ";"]
- _log "wait_for: _csi_$cmd <<<$expect_out(1,string)>>>"
- eval _csi_$cmd $params
- }
- -re "^\[^\x07\x08\x0a\x0d\x1b\]+" {
- _insert $expect_out(0,string)
- }
timeout {
# Assume a timeout means we somehow missed the
# expected result, and carry on.
- warning "timeout in accept_gdb_output"
- dump_screen
+ if { $warn } {
+ warning "timeout in accept_gdb_output following CSI"
+ dump_screen
+ }
+ _insert "^\[\["
return 0
}
}