blob: f0cfa278557bec63784a08e21774567314b8094e [file] [log] [blame]
# Copyright 2022 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/>.
# Test how GDB reformats the documentation string of commands
# implemented in Python for use as the help text of those same
# commands.
load_lib gdb-python.exp
# Check that Python is supported.
clean_restart
if { [skip_python_tests] } { continue }
# A global counter used to number the tests.
set idx 0
# Run a test, create both a command and a parameter with INPUT_DOCS as
# the Python documentation string, load the command and parameter into
# GDB, and then ask for the help text of the command, and the show and
# set help for the parameter. The output from GDB should match
# EXPECTED_OUTPUT in each case.
#
# The INPUT_DOCS must start with 2 space characters, followed by the
# 3-quote characters to start the doc string, and must end with the
# final 3-quote characters. If this is not true then an error is
# thrown, and this function immediately returns.
proc test { input_docs expected_output } {
global idx
set local_idx $idx
incr idx
with_test_prefix "test ${local_idx}" {
# The tests in this script don't have descriptive names,
# rather they use the global IDX to generate a unique name for
# each test. To make it easier to track down a failing test,
# we print out the test name and the input string.
verbose -log "Start of: test_cmd ${local_idx}"
verbose -log "Input:\n${input_docs}"
if { [string range $input_docs 0 4] != " \"\"\"" } {
perror "Input string does not start with the required pattern"
return
}
if { [string range $input_docs end-2 end] != "\"\"\"" } {
perror "Input string does not end with the required pattern"
return
}
set python_filename [standard_output_file "${::gdb_test_file_name}-${local_idx}.py"]
set fd [open $python_filename w]
puts $fd "class test_cmd (gdb.Command):"
puts $fd $input_docs
puts $fd ""
puts $fd " def __init__ (self):"
puts $fd " super ().__init__ (\"test-cmd\", gdb.COMMAND_OBSCURE)"
puts $fd ""
puts $fd " def invoke (self, arg, from_tty):"
puts $fd " print (\"In test-cmd\")"
puts $fd ""
puts $fd "class test_param (gdb.Parameter):"
puts $fd $input_docs
puts $fd ""
puts $fd " show_doc = \"This is the show doc line\""
puts $fd " set_doc = \"This is the set doc line\""
puts $fd ""
puts $fd " def __init__ (self):"
puts $fd " super ().__init__ (\"test-param\", gdb.COMMAND_OBSCURE, gdb.PARAM_BOOLEAN)"
puts $fd ""
puts $fd " def get_show_string (self, value):"
puts $fd " return \"The state is '\" + value + \"'\""
puts $fd ""
puts $fd "test_param ()"
puts $fd "test_cmd ()"
puts $fd ""
puts $fd "print(\"Loaded OK.\")"
close $fd
set remote_python_file \
[gdb_remote_download host $python_filename]
clean_restart
gdb_test "source ${remote_python_file}" \
"Loaded OK\\." \
"source python command file"
# Use gdb_test_multiple here as plain gdb_test will allow
# excess blank lines between the expected_output pattern and
# the gdb_prompt - a core part of this test is that we are
# checking that such blank lines are removed - so we can't use
# gdb_test here.
gdb_test_multiple "help test-cmd" "" {
-re "^help test-cmd\r\n" {
exp_continue
}
-re "^$expected_output\r\n$::gdb_prompt $" {
pass $gdb_test_name
}
}
gdb_test_multiple "help set test-param" "" {
-re "^help set test-param\r\n" {
exp_continue
}
-re "^This is the set doc line\r\n" {
exp_continue
}
-re "^$expected_output\r\n$::gdb_prompt $" {
pass $gdb_test_name
}
}
gdb_test_multiple "help show test-param" "" {
-re "^help show test-param\r\n" {
exp_continue
}
-re "^This is the show doc line\r\n" {
exp_continue
}
-re "^$expected_output\r\n$::gdb_prompt $" {
pass $gdb_test_name
}
}
}
}
# The first test is pretty vanilla. First line starts immediately
# after the opening quotes, and closing quotes are immediately after
# the last line.
test \
[multi_line_input \
" \"\"\"This is the first line." \
"" \
" This is the third line.\"\"\""] \
[multi_line \
"This is the first line\\." \
"" \
"This is the third line\\."]
# In this test the first line starts on the line after the opening
# quotes. The blank line in the middle is still completely empty.
test \
[multi_line_input \
" \"\"\"" \
" This is the first line." \
"" \
" This is the third line.\"\"\""] \
[multi_line \
"This is the first line\\." \
"" \
"This is the third line\\."]
# This test adds an indented line in the middle, we expect the
# relative indentation to be retained.
test\
[multi_line_input \
" \"\"\"" \
" This is the first line." \
" Indented second line." \
" This is the third line.\"\"\""] \
[multi_line \
"This is the first line\\." \
" Indented second line\\." \
"This is the third line\\."]
# The indentation moves to the first line.
test\
[multi_line_input \
" \"\"\"" \
" Indented first line." \
" This is the second line." \
" This is the third line.\"\"\""] \
[multi_line \
" Indented first line\\." \
"This is the second line\\." \
"This is the third line\\."]
# The indentation moves to the last line.
test\
[multi_line_input \
" \"\"\"" \
" This is the first line." \
" This is the second line." \
" Indented third line.\"\"\""] \
[multi_line \
"This is the first line\\." \
"This is the second line\\." \
" Indented third line\\."]
# Tests using different amounts of white-space on a line of its own.
# We test with the white-space at the beginning, end, and in the
# middle of the doc string.
foreach line [list "" " " " " " " " "] {
# Blank lines at the beginning should be removed.
test \
[multi_line_input \
" \"\"\"" \
$line \
" This is the first line." \
" Indented second line." \
" This is the third line.\"\"\""] \
[multi_line \
"This is the first line\\." \
" Indented second line\\." \
"This is the third line\\."]
# As should blank lines at the end.
test \
[multi_line_input \
" \"\"\"" \
" This is the first line." \
" Indented second line." \
" This is the third line." \
$line \
" \"\"\""] \
[multi_line \
"This is the first line\\." \
" Indented second line\\." \
"This is the third line\\."]
# While blank lines in the middle should have all white-space
# removed.
test \
[multi_line_input \
" \"\"\"" \
" This is the first line." \
$line \
" This is the third line." \
$line \
" \"\"\""] \
[multi_line \
"This is the first line\\." \
"" \
"This is the third line\\."]
}
# Check for correct handling of closing quotes being on a line of
# their own.
test\
[multi_line_input \
" \"\"\" " \
" This is the first line." \
" Indented second line." \
" This is the third line." \
" \"\"\""] \
[multi_line \
"This is the first line\\." \
" Indented second line\\." \
"This is the third line\\." ]
# Check with a single 'x' character before the closing quotes. Make
# sure we don't drop this character.
test\
[multi_line_input \
" \"\"\" " \
" This is the first line." \
" Indented second line." \
" This is the third line." \
" x\"\"\""] \
[multi_line \
"This is the first line\\." \
" Indented second line\\." \
"This is the third line\\." \
"x"]