diff options
Diffstat (limited to 'gdb/testsuite/gdb.base')
37 files changed, 1706 insertions, 253 deletions
diff --git a/gdb/testsuite/gdb.base/break-main-file-remove-fail.exp b/gdb/testsuite/gdb.base/break-main-file-remove-fail.exp index eba72bc..080d193 100644 --- a/gdb/testsuite/gdb.base/break-main-file-remove-fail.exp +++ b/gdb/testsuite/gdb.base/break-main-file-remove-fail.exp @@ -88,7 +88,7 @@ proc test_remove_bp { initial_load } { # should warn the user about it. set pagesize [get_integer_valueof "pg_size" 0] set align_addr [expr $bp_addr - $bp_addr % $pagesize] - set munmap [get_integer_valueof "munmap ($align_addr, $pagesize)" -1] + set munmap [get_integer_valueof "(int) munmap ($align_addr, $pagesize)" -1] if {$munmap != 0} { unsupported "can't munmap foo's page" diff --git a/gdb/testsuite/gdb.base/break-probes.exp b/gdb/testsuite/gdb.base/break-probes.exp index 929509a..318a219 100644 --- a/gdb/testsuite/gdb.base/break-probes.exp +++ b/gdb/testsuite/gdb.base/break-probes.exp @@ -86,5 +86,5 @@ if { $using_probes } { } # Call something to ensure that relocation occurred - gdb_test "call foo(23)" "\\\$.* = 31.*\\\M.*" + gdb_test "call (int) foo(23)" "\\\$.* = 31.*\\\M.*" } diff --git a/gdb/testsuite/gdb.base/callfuncs.exp b/gdb/testsuite/gdb.base/callfuncs.exp index 3651963..a537ebd 100644 --- a/gdb/testsuite/gdb.base/callfuncs.exp +++ b/gdb/testsuite/gdb.base/callfuncs.exp @@ -39,7 +39,7 @@ set skip_float_test [gdb_skip_float_test] # specifies that the numeric value of a relational or logical expression # (computed in the inferior) is 1 for true and 0 for false. -proc do_function_calls {} { +proc do_function_calls {prototypes} { global gdb_prompt skip_float_test # We need to up this because this can be really slow on some boards. @@ -95,11 +95,25 @@ proc do_function_calls {} { setup_xfail "mn10300-*-*" if { [test_compiler_info "armcc-*"] } { setup_xfail "*-*-*" } gdb_test "p t_float_values(float_val1,-2.3765)" " = 1" + # Same, via unprototyped function pointer (t_float_values is + # always unprototyped). + gdb_test "p ((int (*) ()) t_float_values)(float_val1,-2.3765)" " = 1" # Test passing of arguments which might not be widened. gdb_test "p t_float_values2(0.0,0.0)" " = 0" + # Same, via function pointer. + if {$prototypes} { + gdb_test "p ((int (*) (float, float)) t_float_values2)(0.0,0.0)" " = 0" + } else { + gdb_test "p ((int (*) ()) t_float_values2)(0.0,0.0)" " = 0" + } gdb_test "p t_float_values2(3.14159,float_val2)" " = 1" + if {$prototypes} { + gdb_test "p ((int (*) (float, float)) t_float_values2)(3.14159,float_val2)" " = 1" + } else { + gdb_test "p ((int (*) ()) t_float_values2)(3.14159,float_val2)" " = 1" + } gdb_test "p t_float_many_args (float_val1, float_val2, float_val3, float_val4, float_val5, float_val6, float_val7, float_val8, float_val9, float_val10, float_val11, float_val12, float_val13, float_val14, float_val15)" " = 1" "call function with many float arguments." @@ -315,7 +329,7 @@ proc rerun_and_prepare {} { "next to t_structs_c" } -proc perform_all_tests {} { +proc perform_all_tests {prototypes} { gdb_test_no_output "set print sevenbit-strings" gdb_test_no_output "set print address off" gdb_test_no_output "set width 0" @@ -326,7 +340,7 @@ proc perform_all_tests {} { set old_reg_content [fetch_all_registers "retrieve original register contents"] # Perform function calls. - do_function_calls + do_function_calls $prototypes # Check if all registers still have the same value. set new_reg_content [fetch_all_registers \ @@ -500,9 +514,11 @@ proc perform_all_tests {} { # Perform all tests with and without function prototypes. if { ![prepare_for_testing "failed to prepare" $testfile $srcfile "$compile_flags additional_flags=-DPROTOTYPES"] } { - perform_all_tests + perform_all_tests 1 } if { ![prepare_for_testing "failed to prepare" $testfile $srcfile "$compile_flags additional_flags=-DNO_PROTOTYPES"] } { - with_test_prefix "noproto" perform_all_tests + with_test_prefix "noproto" { + perform_all_tests 0 + } } diff --git a/gdb/testsuite/gdb.base/checkpoint.exp b/gdb/testsuite/gdb.base/checkpoint.exp index 12c1d8a..677c389 100644 --- a/gdb/testsuite/gdb.base/checkpoint.exp +++ b/gdb/testsuite/gdb.base/checkpoint.exp @@ -224,45 +224,11 @@ gdb_test "shell diff $pi_txt $copy1_txt" \ delete_breakpoints gdb_breakpoint $break2_loc -gdb_test "restart 1" "if .c == EOF.*" "restart 1 three" -gdb_test "continue" "breakpoint 2.*" "break2 1 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 1" - -gdb_test "restart 2" "if .c == EOF.*" "restart 2 three" -gdb_test "continue" "breakpoint 2.*" "break2 2 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 2" - -gdb_test "restart 3" "if .c == EOF.*" "restart 3 three" -gdb_test "continue" "breakpoint 2.*" "break2 3 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 3" - -gdb_test "restart 4" "if .c == EOF.*" "restart 4 three" -gdb_test "continue" "breakpoint 2.*" "break2 4 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 4" - -gdb_test "restart 5" "if .c == EOF.*" "restart 5 three" -gdb_test "continue" "breakpoint 2.*" "break2 5 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 5" - -gdb_test "restart 6" "if .c == EOF.*" "restart 6 three" -gdb_test "continue" "breakpoint 2.*" "break2 6 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 6" - -gdb_test "restart 7" "if .c == EOF.*" "restart 7 three" -gdb_test "continue" "breakpoint 2.*" "break2 7 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 7" - -gdb_test "restart 8" "if .c == EOF.*" "restart 8 three" -gdb_test "continue" "breakpoint 2.*" "break2 8 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 8" - -gdb_test "restart 9" "if .c == EOF.*" "restart 9 three" -gdb_test "continue" "breakpoint 2.*" "break2 9 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 9" - -gdb_test "restart 10" "if .c == EOF.*" "restart 10 three" -gdb_test "continue" "breakpoint 2.*" "break2 10 one" -gdb_test "print ftell (out) > 100000" " = 1.*" "outfile still open 10" +for {set num 1} {$num <= 10} {incr num} { + gdb_test "restart $num" "if .c == EOF.*" "restart $num three" + gdb_test "continue" "breakpoint 2.*" "break2 $num one" + gdb_test "print (long) ftell (out) > 100000" " = 1.*" "outfile still open $num" +} # # Now confirm that if one fork exits, we automatically switch to another one. diff --git a/gdb/testsuite/gdb.base/commands.exp b/gdb/testsuite/gdb.base/commands.exp index 4963743..17f113c 100644 --- a/gdb/testsuite/gdb.base/commands.exp +++ b/gdb/testsuite/gdb.base/commands.exp @@ -34,7 +34,6 @@ proc runto_or_return {function} { } proc_with_prefix gdbvar_simple_if_test {} { - global gdb_prompt global valnum_re gdb_test_no_output "set \$foo = 0" "set foo" @@ -62,7 +61,6 @@ proc_with_prefix gdbvar_simple_if_test {} { } proc_with_prefix gdbvar_simple_while_test {} { - global gdb_prompt global valnum_re gdb_test_no_output "set \$foo = 5" "set foo" @@ -83,7 +81,6 @@ proc_with_prefix gdbvar_simple_while_test {} { } proc_with_prefix gdbvar_complex_if_while_test {} { - global gdb_prompt global valnum_re gdb_test_no_output "set \$foo = 4" "set foo" @@ -107,7 +104,6 @@ proc_with_prefix gdbvar_complex_if_while_test {} { } proc_with_prefix progvar_simple_if_test {} { - global gdb_prompt global valnum_re runto_or_return factorial @@ -139,7 +135,6 @@ proc_with_prefix progvar_simple_if_test {} { } proc_with_prefix progvar_simple_while_test {} { - global gdb_prompt global valnum_re runto_or_return factorial @@ -164,7 +159,6 @@ proc_with_prefix progvar_simple_while_test {} { } proc_with_prefix progvar_complex_if_while_test {} { - global gdb_prompt global valnum_re runto_or_return factorial @@ -289,7 +283,6 @@ proc_with_prefix breakpoint_command_test {} { # Test a simple user defined command (with arguments) proc_with_prefix user_defined_command_test {} { - global gdb_prompt global valnum_re gdb_test_no_output "set \$foo = 4" "set foo" @@ -352,11 +345,38 @@ proc_with_prefix user_defined_command_test {} { "display user-defined empty command" } +# Test that the case with which the command was defined is preserved. + +proc_with_prefix user_defined_command_case_sensitivity {} { + # Define a first command with mixed case name. + set test "define Homer-Simpson" + gdb_test_multiple $test $test { + -re "End with" { + pass $test + } + } + + gdb_test "print 123\nend" "" "enter commands 1" + + # Define a second command, same name but different case. + set test "define HomeR-SimpsoN" + gdb_test_multiple $test $test { + -re "End with" { + pass $test + } + } + + gdb_test "print 456\nend" "" "enter commands 2" + + gdb_test "Homer-Simpson" " = 123" "execute command" + gdb_test "HomeR-SimpsoN" " = 456" "execute command" + gdb_test "HOMER-SIMPSON" "Undefined command.*" "try to call in upper case" + gdb_test "homer-simpson" "Undefined command.*" "try to call in lower case" +} + # Test that "eval" in a user-defined command expands $argc/$argN. proc_with_prefix user_defined_command_args_eval {} { - global gdb_prompt - gdb_test_multiple "define command_args_eval" \ "define command_args_eval" { -re "End with" { @@ -387,8 +407,6 @@ proc_with_prefix user_defined_command_args_eval {} { # user-defined command (or in this case, recurses). proc_with_prefix user_defined_command_args_stack_test {} { - global gdb_prompt - gdb_test_multiple "define args_stack_command" \ "define args_stack_command" { -re "End with" { @@ -444,8 +462,6 @@ proc_with_prefix user_defined_command_args_stack_test {} { # used to have a hard coded limit of 10 arguments. proc_with_prefix user_defined_command_manyargs_test {} { - global gdb_prompt - set test "define command" gdb_test_multiple "define manyargs" $test { -re "End with" { @@ -678,8 +694,6 @@ proc_with_prefix bp_deleted_in_command_test {} { } proc_with_prefix temporary_breakpoint_commands {} { - global gdb_prompt - delete_breakpoints # Create a temporary breakpoint, and associate a commands list to it. @@ -795,8 +809,6 @@ end" } proc gdb_test_no_prompt { command result msg } { - global gdb_prompt - set msg "$command - $msg" set result "^[string_to_regexp $command]\r\n$result$" gdb_test_multiple $command $msg { @@ -943,8 +955,6 @@ proc_with_prefix error_clears_commands_left {} { } proc_with_prefix redefine_hook_test {} { - global gdb_prompt - gdb_test \ [multi_line_input \ "define one"\ @@ -978,8 +988,6 @@ proc_with_prefix redefine_hook_test {} { } proc_with_prefix redefine_backtrace_test {} { - global gdb_prompt - gdb_test_multiple "define backtrace" "define backtrace" { -re "Really redefine built-in command \"backtrace\"\\? \\(y or n\\) $" { pass "define backtrace" @@ -1003,6 +1011,81 @@ proc_with_prefix redefine_backtrace_test {} { gdb_test "bt" "hibob" "execute bt command" } +# Test using "if" and "while" without args when building a command list. + +proc define_if_without_arg_test {} { + foreach cmd {if while} { + set test "define some_command_$cmd" + gdb_test_multiple $test $test { + -re "End with" { + pass $test + } + } + + gdb_test "$cmd" "if/while commands require arguments." "type $cmd without args" + } +} + +# Test the loop_break command. + +proc_with_prefix loop_break_test {} { + gdb_test_no_output "set \$a = 0" "initialize \$a" + gdb_test_no_output "set \$total = 0" "initialize \$total" + + gdb_test \ + [multi_line_input \ + "while \$a < 5" \ + " if \$a == 4" \ + " loop_break" \ + " end" \ + " set \$b = 0" \ + " while \$b < 5" \ + " if \$b == 2" \ + " loop_break" \ + " end" \ + " set \$total = \$total + 1" \ + " set \$b = \$b + 1" \ + " end" \ + " set \$a = \$a + 1" \ + "end"] \ + "" \ + "run while loop" + + gdb_test "print \$a" " = 4" "validate \$a" + gdb_test "print \$b" " = 2" "validate \$b" + gdb_test "print \$total" " = 8" "validate \$total" +} + +# Test the loop_continue command. + +proc_with_prefix loop_continue_test {} { + gdb_test_no_output "set \$a = 0" "initialize \$a" + gdb_test_no_output "set \$total = 0" "initialize \$total" + + gdb_test \ + [multi_line_input \ + "while \$a < 5" \ + " set \$a = \$a + 1" \ + " set \$b = 0" \ + " if \$a == 4" \ + " loop_continue" \ + " end" \ + " while \$b < 5" \ + " set \$b = \$b + 1" \ + " if \$b == 2" \ + " loop_continue" \ + " end" \ + " set \$total = \$total + 1" \ + " end" \ + "end"] \ + "" \ + "run while loop" + + gdb_test "print \$a" " = 5" "validate \$a" + gdb_test "print \$b" " = 5" "validate \$b" + gdb_test "print \$total" " = 16" "validate \$total" +} + # Test an input line split with a continuation character (backslash) # while entering a multi-line command (in a secondary prompt). @@ -1052,6 +1135,7 @@ if_while_breakpoint_command_test infrun_breakpoint_command_test breakpoint_command_test user_defined_command_test +user_defined_command_case_sensitivity user_defined_command_args_eval user_defined_command_args_stack_test user_defined_command_manyargs_test @@ -1067,5 +1151,8 @@ if_commands_test error_clears_commands_left redefine_hook_test backslash_in_multi_line_command_test +define_if_without_arg_test +loop_break_test +loop_continue_test # This one should come last, as it redefines "backtrace". redefine_backtrace_test diff --git a/gdb/testsuite/gdb.base/completion.exp b/gdb/testsuite/gdb.base/completion.exp index 6597ea7..f03bfc3 100644 --- a/gdb/testsuite/gdb.base/completion.exp +++ b/gdb/testsuite/gdb.base/completion.exp @@ -790,7 +790,7 @@ gdb_test_multiple "" $test { -re "break\.c.*break1\.c.*$gdb_prompt " { send_gdb "1\t\n" gdb_test_multiple "" $test { - -re ".*Function \"$srcfile2\" not defined\..*$gdb_prompt " { + -re "malformed linespec error: unexpected end of input\r\n$gdb_prompt " { pass $test } -re "$gdb_prompt p$" { diff --git a/gdb/testsuite/gdb.base/default.exp b/gdb/testsuite/gdb.base/default.exp index 8c0b29c..c25069a 100644 --- a/gdb/testsuite/gdb.base/default.exp +++ b/gdb/testsuite/gdb.base/default.exp @@ -511,7 +511,7 @@ gdb_test "set history size" "Argument required .integer to set it to.*" "set his #test set history gdb_test "set history" "\"set history\" must be followed by the name of a history subcommand.(\[^\r\n\]*\[\r\n\])+List of set history subcommands:(\[^\r\n\]*\[\r\n\])+set history expansion -- Set history expansion on command input(\[^\r\n\]*\[\r\n\])+set history filename -- Set the filename in which to record the command history(\[^\r\n\]*\[\r\n\])+set history save -- Set saving of the history record on exit(\[^\r\n\]*\[\r\n\])+set history size -- Set the size of the command history(\[^\r\n\]*\[\r\n\])+Type \"help set history\" followed by set history subcommand name for full documentation.(\[^\r\n\]*\[\r\n\])+Command name abbreviations are allowed if unambiguous." "set history" #test set language -gdb_test "set language" "Requires an argument. Valid arguments are ada, c, c.., asm, minimal, d, fortran, go, auto, local, unknown, modula-2, objective-c, opencl, pascal, rust." "set language" +gdb_test "set language" "Requires an argument. Valid arguments are auto, local, unknown, ada, asm, c, c.., d, fortran, go, minimal, modula-2, objective-c, opencl, pascal, rust." "set language" #test set listsize gdb_test "set listsize" "Argument required .integer to set it to.*" "set listsize" #test set print "p" abbreviation diff --git a/gdb/testsuite/gdb.base/dfp-test.c b/gdb/testsuite/gdb.base/dfp-test.c index 3af2b4d..a184acb 100644 --- a/gdb/testsuite/gdb.base/dfp-test.c +++ b/gdb/testsuite/gdb.base/dfp-test.c @@ -91,6 +91,23 @@ volatile _Decimal32 d32; volatile _Decimal64 d64; volatile _Decimal128 d128; +/* Typedefs and typedefs of typedefs, for ptype/whatis testing. */ +typedef _Decimal32 d32_t; +typedef _Decimal64 d64_t; +typedef _Decimal128 d128_t; + +typedef d32_t d32_t2; +typedef d64_t d64_t2; +typedef d128_t d128_t2; + +d32_t v_d32_t; +d64_t v_d64_t; +d128_t v_d128_t; + +d32_t2 v_d32_t2; +d64_t2 v_d64_t2; +d128_t2 v_d128_t2; + struct decstruct { int int4; diff --git a/gdb/testsuite/gdb.base/dfp-test.exp b/gdb/testsuite/gdb.base/dfp-test.exp index 5f7b13d..c3a51a4 100644 --- a/gdb/testsuite/gdb.base/dfp-test.exp +++ b/gdb/testsuite/gdb.base/dfp-test.exp @@ -274,6 +274,10 @@ gdb_test "ptype d64 + ds.dec32" " = volatile _Decimal64" gdb_test "ptype d128 + ds.dec32" " = volatile _Decimal128" gdb_test "ptype d128 + ds.dec64" " = volatile _Decimal128" +gdb_test "whatis d64 + ds.dec32" " = volatile _Decimal64" +gdb_test "whatis d128 + ds.dec32" " = volatile _Decimal128" +gdb_test "whatis d128 + ds.dec64" " = volatile _Decimal128" + # Mixture of Decimal and integral operands gdb_test "p d32 + 1" " = 1.1" gdb_test "p 2 + d64" " = 2.1" @@ -331,3 +335,58 @@ gdb_test "print ds.dec128 = -ds.double8" " = 0.(0999.*|1000.*)" gdb_test "print ds.dec128 = ds.dec32" " = -0.1" gdb_test "print ds.dec32 = ds.int4" " = 1" gdb_test "print ds.int4 = 7.3dl" " = 7" + +# Test "whatis"/"ptype" of expressions involving casts to/from dfp +# typedefs. + +# This list is composed by sub-lists, and their elements are (in +# order): +# +# - Type to cast to. This is also what "whatis" should print. +# - What "ptype" should print. + +# Columns in the sublists represent: + # to/whatis # ptype +foreach elem { + {"_Decimal32" "_Decimal32"} + {"_Decimal64" "_Decimal64"} + {"_Decimal128" "_Decimal128"} + {"d32_t" "_Decimal32"} + {"d64_t" "_Decimal64"} + {"d128_t" "_Decimal128"} + {"d32_t2" "_Decimal32"} + {"d64_t2" "_Decimal64"} + {"d128_t2" "_Decimal128"} +} { + set type [lindex $elem 0] + set ptype [lindex $elem 1] + gdb_test "whatis ($type) 0" " = $type" + gdb_test "ptype ($type) 0" " = $ptype" +} + +# Test: +# - whatis/ptype of variables of typedef type. +# - whatis/ptype of typedef type names. +# - whatis/ptype of typedef-of-typedef type names. + +# Columns in the sublists represent: + # Type name # whatis # ptype +foreach elem { + {"v_d32_t" "d32_t" "_Decimal32"} + {"v_d64_t" "d64_t" "_Decimal64"} + {"v_d128_t" "d128_t" "_Decimal128"} + + {"d32_t" "_Decimal32" "_Decimal32"} + {"d64_t" "_Decimal64" "_Decimal64"} + {"d128_t" "_Decimal128" "_Decimal128"} + + {"d32_t2" "d32_t" "_Decimal32"} + {"d64_t2" "d64_t" "_Decimal64"} + {"d128_t2" "d128_t" "_Decimal128"} +} { + set type [lindex $elem 0] + set whatis [lindex $elem 1] + set ptype [lindex $elem 2] + gdb_test "whatis $type" " = $whatis" + gdb_test "ptype $type" " = $ptype" +} diff --git a/gdb/testsuite/gdb.base/dmsym.c b/gdb/testsuite/gdb.base/dmsym.c index f358b51..dccea23 100644 --- a/gdb/testsuite/gdb.base/dmsym.c +++ b/gdb/testsuite/gdb.base/dmsym.c @@ -15,11 +15,11 @@ You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>. */ -int pck__foo__bar__minsym = 123; +static int test_minsym = 123; int -get_pck__foo__bar__minsym (void) +get_test_minsym (void) { - pck__foo__bar__minsym++; - return pck__foo__bar__minsym; + test_minsym++; + return test_minsym; } diff --git a/gdb/testsuite/gdb.base/dmsym.exp b/gdb/testsuite/gdb.base/dmsym.exp index a318080..191a319 100644 --- a/gdb/testsuite/gdb.base/dmsym.exp +++ b/gdb/testsuite/gdb.base/dmsym.exp @@ -44,42 +44,31 @@ clean_restart ${testfile} set num "\[0-9\]+" set addr "0x\[0-9a-zA-Z\]+" -# Although the test program is written in C, the original problem -# occurs only when the language is Ada. The use of a C program is -# only a convenience to be able to exercise the original problem -# without requiring an Ada compiler. In the meantime, temporarily -# force the language to Ada. - -gdb_test_no_output "set lang ada" - -# Verify that setting a breakpoint on `pck__foo__bar__minsym' only -# results in one location found (function pck__foo__bar__minsym__2). -# A mistake would be to also insert a breakpoint where -# pck__foo__bar__minsym is defined. Despite the fact that there is -# no debugging info available, this is a data symbol and thus should -# not be used for breakpoint purposes. - -gdb_test "break pck__foo__bar__minsym" \ +# Verify that setting a breakpoint on `test_minsym' only results in +# one location found. A mistake would be to also insert a breakpoint +# in the test_minsym data symbol in dmsym.c. Despite the fact that +# there is no debugging info available, this is a data symbol and thus +# should not be used for breakpoint purposes. + +gdb_test "break test_minsym" \ "Breakpoint $num at $addr.: file .*dmsym_main\\.c, line $num\\." # However, verify that the `info line' command, on the other hand, # finds both locations. -gdb_test "info line pck__foo__bar__minsym" \ - "Line $num of \".*dmsym_main\\.c\" .*\r\nNo line number information available for address $addr <pck__foo__bar__minsym>" - -gdb_test_no_output "set lang auto" +gdb_test "info line test_minsym" \ + "Line $num of \".*dmsym_main\\.c\" .*\r\nNo line number information available for address $addr <test_minsym>" -# Now, run the program until we get past the call to -# pck__foo__bar__minsym__2. Except when using hardware breakpoints, -# inferior behavior is going to be affected if a breakpoint was -# incorrectly inserted at pck__foo__bar__minsym. +# Now, run the program until we get past the call to test_minsym. +# Except when using hardware breakpoints, inferior behavior is going +# to be affected if a breakpoint was incorrectly inserted at +# test_minsym. gdb_breakpoint dmsym_main.c:[gdb_get_line_number "BREAK" dmsym_main.c] gdb_run_cmd gdb_test "" \ - "Breakpoint $num, pck__foo__bar__minsym__2 \\(\\) at.*" \ + "Breakpoint $num, test_minsym \\(\\) at.*" \ "run until breakpoint at BREAK" gdb_test "continue" \ diff --git a/gdb/testsuite/gdb.base/dmsym_main.c b/gdb/testsuite/gdb.base/dmsym_main.c index 99589b8..0338dc7 100644 --- a/gdb/testsuite/gdb.base/dmsym_main.c +++ b/gdb/testsuite/gdb.base/dmsym_main.c @@ -15,18 +15,18 @@ You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>. */ -extern int get_pck__foo__bar__minsym (void); +extern int get_test_minsym (void); -int -pck__foo__bar__minsym__2 (void) +static int +test_minsym (void) { - return get_pck__foo__bar__minsym (); + return get_test_minsym (); } int main (void) { - int val = pck__foo__bar__minsym__2 (); + int val = test_minsym (); if (val != 124) /* BREAK */ return 1; diff --git a/gdb/testsuite/gdb.base/dprintf-detach.exp b/gdb/testsuite/gdb.base/dprintf-detach.exp index 4c6ef1c..940a9ef 100644 --- a/gdb/testsuite/gdb.base/dprintf-detach.exp +++ b/gdb/testsuite/gdb.base/dprintf-detach.exp @@ -53,7 +53,7 @@ proc dprintf_detach_test { breakpoint_always_inserted dprintf_style disconnected # Get PID of test program. set inferior_pid -1 set test "get inferior process ID" - gdb_test_multiple "call getpid ()" $test { + gdb_test_multiple "call (int) getpid ()" $test { -re ".* = ($decimal).*$gdb_prompt $" { set inferior_pid $expect_out(1,string) pass $test diff --git a/gdb/testsuite/gdb.base/ena-dis-br.exp b/gdb/testsuite/gdb.base/ena-dis-br.exp index 8abca35..d407408 100644 --- a/gdb/testsuite/gdb.base/ena-dis-br.exp +++ b/gdb/testsuite/gdb.base/ena-dis-br.exp @@ -369,7 +369,7 @@ proc test_ena_dis_br { what } { # Now enable(disable) $b1 fooo.1, it should give error on fooo. gdb_test "$what $b1 fooo.1" \ - "Bad breakpoint number 'fooo'" \ + "Bad breakpoint number 'fooo\\.1'" \ "$what \$b1 fooo.1" # $b1 should be enabled(disabled). diff --git a/gdb/testsuite/gdb.base/environ.exp b/gdb/testsuite/gdb.base/environ.exp index 0b69a80..bb52063 100644 --- a/gdb/testsuite/gdb.base/environ.exp +++ b/gdb/testsuite/gdb.base/environ.exp @@ -46,6 +46,9 @@ gdb_test "unset environment" "" "unset all environment variables" \ "Delete all environment variables. .y or n. $" \ "y" +gdb_test_no_output "show environment" \ + "all environment variables have been unset" + # Verify that we can set a specific environment variable. test_set_show_env_var "EDITOR" "emacs" "set environment variable" diff --git a/gdb/testsuite/gdb.base/gnu_vector.exp b/gdb/testsuite/gdb.base/gnu_vector.exp index 44b1405..dac1714 100644 --- a/gdb/testsuite/gdb.base/gnu_vector.exp +++ b/gdb/testsuite/gdb.base/gnu_vector.exp @@ -95,6 +95,17 @@ gdb_test "print -f4a" "\\\$$decimal = \\{-2, -4, -8, -16\\}" gdb_test "print (char4) 0x01010101" "\\\$$decimal = \\{1, 1, 1, 1\\}" gdb_test "print (int2) lla" "\\\$$decimal = \\{1, 1\\}" +# Check that "whatis" doesn't peel off the destination type's typedef +# by mistake, in expressions that involve a cast to typedef type. +gdb_test "whatis (char4) 0x01010101" "type = char4" +gdb_test "whatis (int2) lla" "type = int2" +# Check that OTOH "ptype" does peel off the destination type's +# typedef. +gdb_test "ptype (char4) 0x01010101" \ + "type = char __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" +gdb_test "ptype (int2) lla" \ + "type = int __attribute__ \\(\\(vector_size\\(2\\)\\)\\)" + if { ![string compare $endian big] } then { gdb_test "print (char4) ia" "\\\$$decimal = \\{0, 0, 0, 2\\}" } else { @@ -167,16 +178,30 @@ gdb_test "print (double2) f2" "Cannot convert between vector values of different gdb_test "print (int4) c4" "Cannot convert between vector values of different sizes" gdb_test "print (char4) i4a" "Cannot convert between vector values of different sizes" -# Test ptype on vector types. +# Test ptype/whatis on vector types/vars. gdb_test "ptype c4" "type = char __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" +gdb_test "whatis c4" "type = char4" + gdb_test "ptype char4" "type = char __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" +gdb_test "whatis char4" "type = char __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" + gdb_test "ptype i4a" "type = int __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" +gdb_test "whatis i4a" "type = int4" + gdb_test "ptype int4" "type = int __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" +gdb_test "whatis int4" "type = int __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" + gdb_test "ptype f4b" "type = float __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" +gdb_test "whatis f4b" "type = float4" + gdb_test "ptype float4" "type = float __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" +gdb_test "whatis float4" "type = float __attribute__ \\(\\(vector_size\\(4\\)\\)\\)" gdb_test "ptype union_with_vector_1" "type = union {\r\n\[\t \]+int i;\r\n\[\t \]+char cv __attribute__ \\(\\(vector_size\\(4\\)\\)\\);\r\n}" +gdb_test "whatis union_with_vector_1" {type = union {...}} + gdb_test "ptype struct_with_vector_1" "type = struct {\r\n\[\t \]+int i;\r\n\[\t \]+char cv __attribute__ \\(\\(vector_size\\(4\\)\\)\\);\r\n\[\t \]+float4 f4;\r\n}" +gdb_test "whatis struct_with_vector_1" {type = struct {...}} # Test inferior function calls with vector arguments and/or vector # return values. diff --git a/gdb/testsuite/gdb.base/infcall-exec.exp b/gdb/testsuite/gdb.base/infcall-exec.exp index 3984076..8419905 100644 --- a/gdb/testsuite/gdb.base/infcall-exec.exp +++ b/gdb/testsuite/gdb.base/infcall-exec.exp @@ -44,5 +44,5 @@ append expected_result "\[\r\n\]+.*" append expected_result "Breakpoint 1, main .*at .*$srcfile2:$decimal" append expected_result ".*" -gdb_test "call execlp \(\"$binfile2\", \"$binfile2\", \(char \*\)0\)" \ +gdb_test "call (int) execlp \(\"$binfile2\", \"$binfile2\", \(char \*\)0\)" \ $expected_result "call execlp" diff --git a/gdb/testsuite/gdb.base/info-os.exp b/gdb/testsuite/gdb.base/info-os.exp index 0168ccb..574da26 100644 --- a/gdb/testsuite/gdb.base/info-os.exp +++ b/gdb/testsuite/gdb.base/info-os.exp @@ -39,14 +39,18 @@ if ![runto_main] then { } # Get PID of test program. -set inferior_pid -1 +set inferior_pid "" set test "get inferior process ID" -gdb_test_multiple "call getpid()" $test { +gdb_test_multiple "call (int) getpid()" $test { -re ".* = ($decimal).*$gdb_prompt $" { set inferior_pid $expect_out(1,string) pass $test } } +if {$inferior_pid == ""} { + untested "failed to get pid" + return +} gdb_breakpoint ${srcfile}:[gdb_get_line_number "Set breakpoint here"] gdb_continue_to_breakpoint "Set breakpoint here" diff --git a/gdb/testsuite/gdb.base/list-ambiguous.exp b/gdb/testsuite/gdb.base/list-ambiguous.exp new file mode 100644 index 0000000..ace3494 --- /dev/null +++ b/gdb/testsuite/gdb.base/list-ambiguous.exp @@ -0,0 +1,79 @@ +# Copyright 2017 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 the "list" command with linespecs that expand to multiple +# locations. + +standard_testfile list-ambiguous0.c list-ambiguous1.c + +if {[prepare_for_testing "failed to prepare" $testfile [list $srcfile $srcfile2] \ + {debug}]} { + return -1 +} + +# Build source listing pattern based on an inclusive line range. + +proc line_range_pattern { range_start range_end } { + global line_re + + for {set i $range_start} {$i <= $range_end} {incr i} { + append pattern "\r\n$i\[ \t\]\[^\r\n\]*" + } + + verbose -log "pattern $pattern" + return $pattern +} + +# Test the "list" command with linespecs that expand to multiple +# locations. + +proc test_list_ambiguous_symbol {symbol_line symbol} { + global srcfile srcfile2 + + set lineno0 [gdb_get_line_number $symbol_line $srcfile] + set lineno1 [gdb_get_line_number $symbol_line $srcfile2] + set lines0_re [line_range_pattern [expr $lineno0 - 5] [expr $lineno0 + 4]] + set lines1_re [line_range_pattern [expr $lineno1 - 5] [expr $lineno1 + 4]] + + set any "\[^\r\n\]*" + set h0_re "file: \"${any}list-ambiguous0.c\", line number: $lineno0, symbol: \"$symbol\"" + set h1_re "file: \"${any}list-ambiguous1.c\", line number: $lineno1, symbol: \"$symbol\"" + gdb_test "list $symbol" "${h0_re}${lines0_re}\r\n${h1_re}${lines1_re}" + + gdb_test "list main,$symbol" \ + "Specified last line '$symbol' is ambiguous:\r\n${h0_re}\r\n${h1_re}" + gdb_test "list ,$symbol" \ + "Specified last line '$symbol' is ambiguous:\r\n${h0_re}\r\n${h1_re}" + gdb_test "list $symbol,main" \ + "Specified first line '$symbol' is ambiguous:\r\n${h0_re}\r\n${h1_re}" + gdb_test "list $symbol,$symbol" \ + "Specified first line '$symbol' is ambiguous:\r\n${h0_re}\r\n${h1_re}" + gdb_test "list $symbol," \ + "Specified first line '$symbol' is ambiguous:\r\n${h0_re}\r\n${h1_re}" + + # While at it, test the "edit" command as well, since it shares + # code with "list". + gdb_test "edit $symbol" \ + "Specified line is ambiguous:\r\n${h0_re}\r\n${h1_re}" +} + +proc test_list_ambiguous_function {} { + test_list_ambiguous_symbol "ambiguous_fun (void)" "ambiguous_fun" + test_list_ambiguous_symbol "ambiguous_var" "ambiguous_var" +} + +gdb_test_no_output "set listsize 10" + +test_list_ambiguous_function diff --git a/gdb/testsuite/gdb.base/list-ambiguous0.c b/gdb/testsuite/gdb.base/list-ambiguous0.c new file mode 100644 index 0000000..afd9457 --- /dev/null +++ b/gdb/testsuite/gdb.base/list-ambiguous0.c @@ -0,0 +1,42 @@ +/* This testcase is part of GDB, the GNU debugger. + + Copyright 2017 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/>. */ + + + + + +/* These symbols are defined in both + list-ambiguous0.c/list-ambiguous1.c files, in order to test + "list"'s behavior with ambiguous linespecs. */ + +static void __attribute__ ((used)) ambiguous_fun (void) {} + +static int ambiguous_var; + + + + + + + + + +int +main (void) +{ + return 0; +} diff --git a/gdb/testsuite/gdb.base/list-ambiguous1.c b/gdb/testsuite/gdb.base/list-ambiguous1.c new file mode 100644 index 0000000..69db11e --- /dev/null +++ b/gdb/testsuite/gdb.base/list-ambiguous1.c @@ -0,0 +1,41 @@ +/* This testcase is part of GDB, the GNU debugger. + + Copyright 2017 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/>. */ + + + + + + + + + +/* These symbols are defined in both + list-ambiguous0.c/list-ambiguous1.c files, in order to test + "list"'s behavior with ambiguous linespecs. */ +static void __attribute__ ((used)) ambiguous_fun (void) {} + +static int ambiguous_var; + + + + + + + + + +/* last line */ diff --git a/gdb/testsuite/gdb.base/list.exp b/gdb/testsuite/gdb.base/list.exp index 5377571..d554c9e 100644 --- a/gdb/testsuite/gdb.base/list.exp +++ b/gdb/testsuite/gdb.base/list.exp @@ -361,7 +361,7 @@ proc test_list_range {} { gdb_test "list ${past_end},${much_past_end}" "Line number ${past_end} out of range; .*list0.c has ${last_line} lines." "list range; both bounds past EOF" - gdb_test "list list0.c:2,list1.c:17" "Specified start and end are in different files." "list range, must be same files" + gdb_test "list list0.c:2,list1.c:17" "Specified first and last lines are in different files." "list range, must be same files" } # diff --git a/gdb/testsuite/gdb.base/nodebug.c b/gdb/testsuite/gdb.base/nodebug.c index eb5d661..c7bc939 100644 --- a/gdb/testsuite/gdb.base/nodebug.c +++ b/gdb/testsuite/gdb.base/nodebug.c @@ -1,4 +1,6 @@ #include <stdlib.h> +#include <stdint.h> + /* Test that things still (sort of) work when compiled without -g. */ int dataglobal = 3; /* Should go in global data */ @@ -6,6 +8,13 @@ static int datalocal = 4; /* Should go in local data */ int bssglobal; /* Should go in global bss */ static int bsslocal; /* Should go in local bss */ +/* Non-int-sized global data variables. */ +uint8_t dataglobal8 = 0xff; +uint32_t dataglobal32_1 = 0x7fffffff; +uint32_t dataglobal32_2 = 0x000000ff; +uint64_t dataglobal64_1 = 0x7fffffffffffffff; +uint64_t dataglobal64_2 = 0x00000000000000ff; + int inner (int x) { @@ -43,3 +52,42 @@ int array_index (char *arr, int i) free (x); return retval; } + +float +multf (float v1, float v2) +{ + return v1 * v2; +} + +float +multf_noproto (v1, v2) + float v1, v2; +{ + return v1 * v2; +} + +double +mult (double v1, double v2) +{ + return v1 * v2; +} + +double +mult_noproto (v1, v2) + double v1, v2; +{ + return v1 * v2; +} + +uint8_t +add8 (uint8_t v1, uint8_t v2) +{ + return v1 + v2; +} + +uint8_t +add8_noproto (v1, v2) + uint8_t v1, v2; +{ + return v1 + v2; +} diff --git a/gdb/testsuite/gdb.base/nodebug.exp b/gdb/testsuite/gdb.base/nodebug.exp index a54e5bb..3a2a821 100644 --- a/gdb/testsuite/gdb.base/nodebug.exp +++ b/gdb/testsuite/gdb.base/nodebug.exp @@ -39,7 +39,56 @@ if { [gdb_compile $srcdir/$subdir/$srcfile $binfile executable $exec_opts] != " clean_restart $binfile -if [runto inner] then { +# Run to FUNC and unload symbols from system shared libraries, to +# avoid conflicts with the minsyms in the program. E.g., +# intl/plural-exp.h has 'enum expression_operator {..., mult, ...}'. + +proc nodebug_runto {func} { + with_test_prefix $func { + if ![runto $func] { + return false + } + gdb_test_no_output "nosharedlibrary" \ + "unload symbols from system libraries" + return true + } +} + +# Test calling no-debug functions involving argument types that may +# require coercion/promotion, both prototyped and unprototyped, both +# return-type-cast style, and function-pointer-cast styles. +proc test_call_promotion {} { + if [target_info exists gdb,cannot_call_functions] { + return + } + + # Call prototyped function with float parameters via both + # return-type cast and function-pointer cast. This checks that + # GDB doesn't do float->double coercion. + gdb_test "p (float) multf(2.0f, 3.0f)" " = 6" + gdb_test "p ((float (*) (float, float)) multf)(2, 3)" " = 6" + gdb_test "p ((float (*) (float, float)) multf)(2.0f, 3.0f)" " = 6" + + # Call unprototyped function with float parameters via + # function-pointer cast, only. return-type cast assumes + # protototyped. Check that GDB does float->double coercion. + gdb_test "p ((float (*) ()) multf_noproto)(2.0f, 3.0f)" " = 6" + gdb_test "p ((float (*) ()) multf_noproto)(2.0, 3.0)" " = 6" + + # Same, but for double. + gdb_test "p (double) mult (2.0, 3.0)" " = 6" + gdb_test "p ((double (*) (double, double)) mult)(2.0f, 3.0f)" " = 6" + gdb_test "p ((double (*) (double, double)) mult)(2, 3)" " = 6" + gdb_test "p ((double (*) ()) mult_noproto)(2.0f, 3.0f)" " = 6" + gdb_test "p ((double (*) ()) mult_noproto)(2.0, 3.0)" " = 6" + + # Check that GDB promotes char->int correctly. + gdb_test "p /d (uint8) add8((uint8) 2, (uint8) 3)" " = 5" + gdb_test "p /d ((uint8 (*) (uint8, uint8)) add8)((uint8) 2, (uint8) 3)" " = 5" + gdb_test "p /d ((uint8 (*) ()) add8_noproto)((uint8) 2, (uint8) 3)" " = 5" +} + +if [nodebug_runto inner] then { # Expect to find global/local symbols in each of text/data/bss. @@ -59,22 +108,116 @@ if [runto inner] then { # out debugging info for non-aggregate return values of functions # even without -g, which should be accepted. - gdb_test "p top" \ - "\{(<(text variable|function), no debug info>|short \\(int\\)|short \\(\\))\} \[0-9a-fx]* <\\.?top(\\(int\\)|)>" - gdb_test "whatis top" \ - "(<(text variable|function), no debug info>|short \\(int\\)|short \\(\\))" - gdb_test "ptype top" "(short|int) \\((|void|int|<non-float parameter>|<non-float parameter>, <non-float parameter>)\\)" - - gdb_test "p middle" \ - "\{(<(text variable|function), no debug info>|short \\(int\\)|short \\(\\))\} \[0-9a-fx]* <\\.?middle(\\(int\\)|)>" - gdb_test "whatis middle" \ - "(<(text variable|function), no debug info>|short \\(int\\)|short \\(\\))" - gdb_test "ptype middle" "(short|int) \\((|void|int|<non-float parameter>|<non-float parameter>, <non-float parameter>)\\)" - - gdb_test "p dataglobal" "= 3" - gdb_test "whatis dataglobal" \ - "<(data variable|variable), no debug info>|int" - gdb_test "ptype dataglobal" "<(data variable|variable), no debug info>|int" + with_test_prefix "func" { + # Most languages default to printing like C. + set c_print_re " = \\{<text variable, no debug info>\\} $hex <top>" + set c_whatis_re " = <text variable, no debug info>" + set c_ptype_re "= <unknown return type> \\(\\)" + + set cxx_ptype_re "= <unknown return type> \\(void\\)" + + set ada_ptype_re " = function return <unknown return type>" + + set m2_print_re " = \\{PROCEDURE <text variable, no debug info> \\(\\) : <unknown return type>\\} $hex <top>" + set m2_whatis_re "PROCEDURE <text variable, no debug info> \\(\\) : <unknown return type>" + set m2_ptype_re $m2_whatis_re + + # Rust can't access minsyms? + set rust_nosym "No symbol 'top' in current context" + + set pascal_ptype_re "type = procedure : <unknown return type>" + + #LANG #PRINT #WHATIS #PTYPE + foreach lang_line { + {"ada" $c_print_re $c_whatis_re $ada_ptype_re} + {"asm" $c_print_re $c_whatis_re $c_ptype_re} + {"c" $c_print_re $c_whatis_re $c_ptype_re} + {"c++" $c_print_re $c_whatis_re $cxx_ptype_re} + {"d" $c_print_re $c_whatis_re $c_ptype_re} + {"fortran" $c_print_re $c_whatis_re $c_ptype_re} + {"go" $c_print_re $c_whatis_re $c_ptype_re} + {"minimal" $c_print_re $c_whatis_re $c_ptype_re} + {"modula-2" $m2_print_re $m2_whatis_re $m2_ptype_re} + {"objective-c" $c_print_re $c_whatis_re $c_ptype_re} + {"opencl" $c_print_re $c_whatis_re $c_ptype_re} + {"pascal" $c_print_re $c_whatis_re $pascal_ptype_re} + {"rust" $rust_nosym $rust_nosym $rust_nosym} + } { + set lang [lindex $lang_line 0] + set print_re [lindex $lang_line 1] + set whatis_re [lindex $lang_line 2] + set ptype_re [lindex $lang_line 3] + + set print_re [subst "$print_re"] + set whatis_re [subst "$whatis_re"] + set ptype_re [subst "$ptype_re"] + + with_test_prefix "$lang" { + gdb_test_no_output "set language $lang" + gdb_test "p top" $print_re + gdb_test "whatis top" $whatis_re + gdb_test "ptype top" $ptype_re + } + } + } + + gdb_test_no_output "set language auto" + + # We can't rely on uintXX_t being available/known to GDB because + # we may or may not have debug info for those (depending on + # whether we have debug info for the C runtime, for example). + gdb_test_no_output "macro define uint8 unsigned char" + gdb_test_no_output "macro define uint32 unsigned int" + gdb_test_no_output "macro define uint64 unsigned long long" + + set data_var_type "<data variable, no debug info>" + set unk_type_re "has unknown type.*to its declared type" + set ptr_math_re "Cannot perform pointer math on incomplete type \"$data_var_type\", try casting to a known type, or void \\*\\." + set not_mem_re "Attempt to take address of value not located in memory\\." + + set dataglobal_unk_re "dataglobal.*$unk_type_re" + + #exp #fmt #print #ptype/whatis + foreach line { + {"dataglobal" "" $dataglobal_unk_re " = $data_var_type"} + {"(int) dataglobal" "" "= 3" " = int"} + {"sizeof(dataglobal)" "" $dataglobal_unk_re $dataglobal_unk_re} + {"sizeof(dataglobal + 1)" "" $dataglobal_unk_re $dataglobal_unk_re} + {"sizeof((int) dataglobal)" "" " = $decimal" " = int"} + {"dataglobal + 1" "" $dataglobal_unk_re $dataglobal_unk_re} + {"&dataglobal" "" "\\($data_var_type \\*\\) $hex <dataglobal>" " = $data_var_type \\*"} + {"&dataglobal + 1" "" $ptr_math_re $ptr_math_re} + {"(int *) &dataglobal + 1" "" " = \\(int \\*\\) $hex <datalocal>" "int \\*"} + {"&(int) dataglobal + 1" "" $not_mem_re $not_mem_re} + {"&dataglobal, &dataglobal" "" "\\($data_var_type \\*\\) $hex <dataglobal>" " = $data_var_type \\*"} + {"*dataglobal" "" $dataglobal_unk_re $dataglobal_unk_re} + + {"dataglobal8" "/x" $dataglobal_unk_re " = $data_var_type"} + {"(uint8) dataglobal8" "/x" " = 0xff" "unsigned char"} + + {"dataglobal32_1" "/x" $dataglobal_unk_re " = $data_var_type"} + {"(uint32) dataglobal32_1" "/x" " = 0x7fffffff" "unsigned int"} + {"dataglobal32_2" "/x" $dataglobal_unk_re " = $data_var_type"} + {"(uint32) dataglobal32_2" "/x" " = 0xff" "unsigned int"} + + {"dataglobal64_1" "/x" $dataglobal_unk_re " = $data_var_type"} + {"(uint64) dataglobal64_1" "/x" " = 0x7fffffffffffffff" "unsigned long long"} + {"dataglobal64_2" "/x" $dataglobal_unk_re " = $data_var_type"} + {"(uint64) dataglobal64_2" "/x" " = 0xff" "unsigned long long"} + } { + set exp [lindex $line 0] + # Expand variables. + set fmt [subst -nobackslashes [lindex $line 1]] + set print [subst -nobackslashes [lindex $line 2]] + set whatis [subst -nobackslashes [lindex $line 3]] + if {$fmt == ""} { + gdb_test "p $exp" $print + } else { + gdb_test "p $fmt $exp" $print + } + gdb_test "whatis $exp" $whatis + gdb_test "ptype $exp" $whatis + } # The only symbol xcoff puts out for statics is for the TOC entry. # Possible, but hairy, for gdb to deal. Right now it doesn't, it @@ -82,35 +225,39 @@ if [runto inner] then { setup_xfail "rs6000*-*-aix*" setup_xfail "powerpc*-*-aix*" - gdb_test "p datalocal" "= 4" + gdb_test "p datalocal" "datalocal.*$unk_type_re" + gdb_test "p (int) datalocal" "= 4" setup_xfail "rs6000*-*-aix*" setup_xfail "powerpc*-*-aix*" - gdb_test "whatis datalocal" "<(data variable|variable), no debug info>" + gdb_test "whatis datalocal" "datalocal.*$data_var_type" setup_xfail "rs6000*-*-aix*" setup_xfail "powerpc*-*-aix*" - gdb_test "ptype datalocal" "<(data variable|variable), no debug info>" - gdb_test "p bssglobal" "= 0" - gdb_test "whatis bssglobal" "<(data variable|variable), no debug info>|int" - gdb_test "ptype bssglobal" "<(data variable|variable), no debug info>|int" + gdb_test "ptype datalocal" "datalocal.*$data_var_type" + + gdb_test "p bssglobal" "bssglobal.*$unk_type_re" + gdb_test "p (int) bssglobal" "= 0" + gdb_test "whatis bssglobal" $data_var_type + gdb_test "ptype bssglobal" $data_var_type setup_xfail "rs6000*-*-aix*" setup_xfail "powerpc*-*-aix*" - gdb_test "p bsslocal" "= 0" + gdb_test "p bsslocal" "bsslocal.*$unk_type_re" + gdb_test "p (int) bsslocal" "= 0" setup_xfail "rs6000*-*-aix*" setup_xfail "powerpc*-*-aix*" - gdb_test "whatis bsslocal" "<(data variable|variable), no debug info>" + gdb_test "whatis bsslocal" $data_var_type setup_xfail "rs6000*-*-aix*" setup_xfail "powerpc*-*-aix*" - gdb_test "ptype bsslocal" "<(data variable|variable), no debug info>" + gdb_test "ptype bsslocal" $data_var_type gdb_test "backtrace 10" "#0.*inner.*#1.*middle.*#2.*top.*#3.*main.*" \ "backtrace from inner in nodebug.exp" @@ -122,20 +269,26 @@ if [runto inner] then { # This test is not as obscure as it might look. `p getenv ("TERM")' # is a real-world example, at least on many systems. + foreach cmd {"p/c" "ptype" "whatis"} { + gdb_test "$cmd array_index(\"abcdef\",2)" \ + "'array_index' has unknown return type; cast the call to its declared return type" + } if [target_info exists gdb,cannot_call_functions] { - unsupported "p/c array_index(\"abcdef\",2)" + unsupported "p/c (int) array_index(\"abcdef\",2)" } else { # We need to up this because this can be really slow on some boards. # (malloc() is called as part of the test). set prev_timeout $timeout set timeout 60 - gdb_test {p/c array_index("abcdef",2)} " = 99 'c'" + gdb_test {p/c (int) array_index("abcdef",2)} " = 99 'c'" set timeout $prev_timeout } - + + test_call_promotion + # Now, try that we can give names of file-local symbols which happen # to be unique, and have it still work - if [runto middle] then { + if [nodebug_runto middle] then { gdb_test "backtrace 10" "#0.*middle.*#1.*top.*#2.*main.*" \ "backtrace from middle in nodebug.exp" } diff --git a/gdb/testsuite/gdb.base/printcmds.exp b/gdb/testsuite/gdb.base/printcmds.exp index 323ca73..9409c6a 100644 --- a/gdb/testsuite/gdb.base/printcmds.exp +++ b/gdb/testsuite/gdb.base/printcmds.exp @@ -155,6 +155,16 @@ proc test_float_rejected {} { test_print_reject "p 1.1ll" } +# Regression test for PR gdb/21675 +proc test_radices {} { + gdb_test "print/o 16777211" " = 077777773" + gdb_test "print/d 1.5" " = 1" + gdb_test "print/u 1.5" " = 1" + + gdb_test "print/u (char) -1" " = 255" + gdb_test "print/d (unsigned char) -1" " = -1" +} + proc test_print_all_chars {} { global gdb_prompt @@ -981,3 +991,4 @@ test_printf test_printf_with_dfp test_print_symbol test_repeat_bytes +test_radices diff --git a/gdb/testsuite/gdb.base/reread.exp b/gdb/testsuite/gdb.base/reread.exp index cc0f577..4e611ce 100644 --- a/gdb/testsuite/gdb.base/reread.exp +++ b/gdb/testsuite/gdb.base/reread.exp @@ -15,111 +15,131 @@ set prototypes 1 -# build the first test case +# Build programs in PIE mode, to reproduce PR 21555. +foreach_with_prefix opts { + { "" "" } + { "-fPIE" "ldflags=-pie" } } { -set testfile1 "reread1" -set srcfile1 ${testfile1}.c -# Cygwin needs $EXEEXT. -set binfile1 [standard_output_file ${testfile1}$EXEEXT] - -if { [gdb_compile "${srcdir}/${subdir}/${srcfile1}" "${binfile1}" executable {debug nowarnings}] != "" } { - untested "failed to compile first testcase" - return -1 -} - -# build the second test case - -set testfile2 "reread2" -set srcfile2 ${testfile2}.c -set binfile2 [standard_output_file ${testfile2}$EXEEXT] - -if { [gdb_compile "${srcdir}/${subdir}/${srcfile2}" "${binfile2}" executable {debug nowarnings}] != "" - && [gdb_compile "${srcdir}/${subdir}/${srcfile2}" "${binfile2}" executable {debug nowarnings additional_flags=-DNO_SECTIONS}] != ""} { - untested "failed to compile second testcase" - return -1 -} - -# Start with a fresh gdb. - -set testfile "reread" -set binfile [standard_output_file ${testfile}$EXEEXT] - -gdb_start -gdb_reinitialize_dir $srcdir/$subdir - -# Load the first executable. - -gdb_rename_execfile ${binfile1} ${binfile} -gdb_load ${binfile} - -# Set a breakpoint at foo - -gdb_test "break foo" \ - "Breakpoint.*at.* file .*$srcfile1, line 14.*" \ - "breakpoint foo in first file" - - -# Run, should see "Breakpoint 1, foo () at hello1.c:14" - -gdb_run_cmd -gdb_test "" "Breakpoint.* foo .* at .*$srcfile1:14.*" "run to foo()" - -# Restore first executable to its original name, and move -# second executable into its place. Ensure that the new -# executable is at least a second newer than the old. - -gdb_rename_execfile ${binfile} ${binfile1} -gdb_rename_execfile ${binfile2} ${binfile} -gdb_test "shell sleep 1" ".*" "" -gdb_touch_execfile ${binfile} - -# Run a second time; GDB should detect that the executable has changed -# and reset the breakpoints correctly. -# Should see "Breakpoint 1, foo () at reread2.c:9" - -set test "run to foo() second time" -if [is_remote target] { - unsupported $test -} else { - gdb_run_cmd - gdb_test "" "Breakpoint.* foo .* at .*:9.*" $test -} - - -### Second pass: verify that GDB checks the executable file's -### timestamp when the program is *restarted*, not just when it exits. - -if [is_remote target] { - unsupported "second pass: GDB should check for changes before running" -} else { - - # Put the older executable back in place. - gdb_rename_execfile ${binfile} ${binfile2} - gdb_rename_execfile ${binfile1} ${binfile} - - # Restart GDB entirely. - clean_restart ${binfile} - - # Set a breakpoint on foo and run to it. - gdb_test "break foo" \ - "Breakpoint.*at.* file .*$srcfile1, line 14.*" \ - "second pass: breakpoint foo in first file" - gdb_run_cmd - gdb_test "" "Breakpoint.* foo .* at .*$srcfile1:14.*" "second pass: run to foo()" - - # This time, let the program run to completion. If GDB checks the - # executable file's timestamp now, it won't notice any change. - gdb_continue_to_end "second pass" - - # Now move the newer executable into place, and re-run. GDB - # should still notice that the executable file has changed, - # and still re-set the breakpoint appropriately. - gdb_rename_execfile ${binfile} ${binfile1} - gdb_rename_execfile ${binfile2} ${binfile} - gdb_run_cmd - gdb_test "" "Breakpoint.* foo .* at .*:9.*" "second pass: run to foo() second time" -} + # build the first test case + set testfile1 "reread1" + set srcfile1 ${testfile1}.c + # Cygwin needs $EXEEXT. + set binfile1 [standard_output_file ${testfile1}$EXEEXT] + + set testfile1_opt [list debug nowarnings \ + additional_flags=[lindex $opts 0] \ + [lindex $opts 1] ] + if { [gdb_compile "${srcdir}/${subdir}/${srcfile1}" "${binfile1}" \ + executable ${testfile1_opt}] != "" } { + untested "failed to compile first testcase" + return -1 + } + + # build the second test case + + set testfile2 "reread2" + set srcfile2 ${testfile2}.c + set binfile2 [standard_output_file ${testfile2}$EXEEXT] + + set testfile2_opt1 [list debug nowarnings \ + additional_flags=[lindex $opts 0] \ + [lindex $opts 1]] + set testfile2_op2 [list debug nowarnings \ + "additional_flags=-DNO_SECTIONS [lindex $opts 0]" \ + [lindex $opts 1]] + if { [gdb_compile "${srcdir}/${subdir}/${srcfile2}" "${binfile2}" \ + executable ${testfile2_opt1}] != "" + && [gdb_compile "${srcdir}/${subdir}/${srcfile2}" "${binfile2}" \ + executable ${testfile2_opt2}] != ""} { + untested "failed to compile second testcase" + return -1 + } + + # Start with a fresh gdb. + + set testfile "reread" + set binfile [standard_output_file ${testfile}$EXEEXT] + + gdb_start + gdb_reinitialize_dir $srcdir/$subdir + + # Load the first executable. + + gdb_rename_execfile ${binfile1} ${binfile} + gdb_load ${binfile} + + # Set a breakpoint at foo + + gdb_test "break foo" \ + "Breakpoint.*at.* file .*$srcfile1, line 14.*" \ + "breakpoint foo in first file" + + + # Run, should see "Breakpoint 1, foo () at hello1.c:14" + + gdb_run_cmd + gdb_test "" "Breakpoint.* foo .* at .*$srcfile1:14.*" "run to foo()" + + # Restore first executable to its original name, and move + # second executable into its place. Ensure that the new + # executable is at least a second newer than the old. + + gdb_rename_execfile ${binfile} ${binfile1} + gdb_rename_execfile ${binfile2} ${binfile} + gdb_test "shell sleep 1" ".*" "" + gdb_touch_execfile ${binfile} + + # Run a second time; GDB should detect that the executable has changed + # and reset the breakpoints correctly. + # Should see "Breakpoint 1, foo () at reread2.c:9" + + set test "run to foo() second time" + if [is_remote target] { + unsupported $test + } else { + gdb_run_cmd + gdb_test "" "Breakpoint.* foo .* at .*:9.*" $test + } + + + ### Second pass: verify that GDB checks the executable file's + ### timestamp when the program is *restarted*, not just when it exits. + + if [is_remote target] { + unsupported "second pass: GDB should check for changes before running" + } else { + + # Put the older executable back in place. + gdb_rename_execfile ${binfile} ${binfile2} + gdb_rename_execfile ${binfile1} ${binfile} + + # Restart GDB entirely. + clean_restart ${binfile} + + # Set a breakpoint on foo and run to it. + gdb_test "break foo" \ + "Breakpoint.*at.* file .*$srcfile1, line 14.*" \ + "second pass: breakpoint foo in first file" + gdb_run_cmd + gdb_test "" "Breakpoint.* foo .* at .*$srcfile1:14.*" \ + "second pass: run to foo()" + + # This time, let the program run to completion. If GDB checks the + # executable file's timestamp now, it won't notice any change. + gdb_continue_to_end "second pass" + + # Now move the newer executable into place, and re-run. GDB + # should still notice that the executable file has changed, + # and still re-set the breakpoint appropriately. + gdb_rename_execfile ${binfile} ${binfile1} + gdb_rename_execfile ${binfile2} ${binfile} + gdb_run_cmd + gdb_test "" "Breakpoint.* foo .* at .*:9.*" \ + "second pass: run to foo() second time" + } + + } # End of tests. return 0 diff --git a/gdb/testsuite/gdb.base/share-env-with-gdbserver.c b/gdb/testsuite/gdb.base/share-env-with-gdbserver.c new file mode 100644 index 0000000..740bd0f --- /dev/null +++ b/gdb/testsuite/gdb.base/share-env-with-gdbserver.c @@ -0,0 +1,40 @@ +/* This testcase is part of GDB, the GNU debugger. + + Copyright 2017 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/>. */ + +#include <stdio.h> +#include <stdlib.h> + +/* Wrapper around getenv for GDB. */ + +static const char * +my_getenv (const char *name) +{ + return getenv (name); +} + +int +main (int argc, char *argv[]) +{ + const char *myvar = getenv ("GDB_TEST_VAR"); + + if (myvar != NULL) + printf ("It worked! myvar = '%s'\n", myvar); + else + printf ("It failed."); + + return 0; /* break-here */ +} diff --git a/gdb/testsuite/gdb.base/share-env-with-gdbserver.exp b/gdb/testsuite/gdb.base/share-env-with-gdbserver.exp new file mode 100644 index 0000000..7521be1 --- /dev/null +++ b/gdb/testsuite/gdb.base/share-env-with-gdbserver.exp @@ -0,0 +1,255 @@ +# This testcase is part of GDB, the GNU debugger. + +# Copyright 2017 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/>. + +# This test doesn't make sense on native-gdbserver. +if { [use_gdb_stub] } { + untested "not supported" + return +} + +standard_testfile + +if { [prepare_for_testing "failed to prepare" $testfile $srcfile debug] } { + return -1 +} + +set test_var_name "GDB_TEST_VAR" + +# Helper function that performs a check on the output of "getenv". +# +# - VAR_NAME is the name of the variable to be checked. +# +# - VAR_VALUE is the value expected. +# +# - TEST_MSG, if not empty, is the test message to be used by the +# "gdb_test". +# +# - EMPTY_VAR_P, if non-zero, means that the variable is not expected +# to exist. In this case, VAR_VALUE is not considered. + +proc check_getenv { var_name var_value { test_msg "" } { empty_var_p 0 } } { + global hex decimal + + if { $test_msg == "" } { + set test_msg "print result of getenv for $var_name" + } + + if { $empty_var_p } { + set var_value_match "0x0" + } else { + set var_value_match "$hex \"$var_value\"" + } + + gdb_test "print my_getenv (\"$var_name\")" "\\\$$decimal = $var_value_match" \ + $test_msg +} + +# Helper function to re-run to main and breaking at the "break-here" +# label. + +proc do_prepare_inferior { } { + global decimal hex + + if { ![runto_main] } { + return -1 + } + + gdb_breakpoint [gdb_get_line_number "break-here"] + + gdb_test "continue" "Breakpoint $decimal, main \\\(argc=1, argv=$hex\\\) at.*" \ + "continue until breakpoint" +} + +# Helper function that does the actual testing. +# +# - VAR_VALUE is the value of the environment variable. +# +# - VAR_NAME is the name of the environment variable. If empty, +# defaults to $test_var_name. +# +# - VAR_NAME_MATCH is the name (regex) that will be used to query the +# environment about the variable (via getenv). This is useful when +# we're testing variables with strange names (e.g., with an equal +# sign in the name) and we know that the variable will actually be +# set using another name. If empty, defatults, to $var_name. +# +# - VAR_VALUE_MATCH is the value (regex) that will be used to match +# the result of getenv. The rationale is the same as explained for +# VAR_NAME_MATCH. If empty, defaults, to $var_value. + +proc do_test { var_value { var_name "" } { var_name_match "" } { var_value_match "" } } { + global binfile test_var_name + + clean_restart $binfile + + if { $var_name == "" } { + set var_name $test_var_name + } + + if { $var_name_match == "" } { + set var_name_match $var_name + } + + if { $var_value_match == "" } { + set var_value_match $var_value + } + + if { $var_value != "" } { + gdb_test_no_output "set environment $var_name = $var_value" \ + "set $var_name = $var_value" + } else { + gdb_test "set environment $var_name =" \ + "Setting environment variable \"$var_name\" to null value." \ + "set $var_name to null value" + } + + do_prepare_inferior + + check_getenv "$var_name_match" "$var_value_match" \ + "print result of getenv for $var_name" +} + +with_test_prefix "long var value" { + do_test "this is my test variable; testing long vars; {}" +} + +with_test_prefix "empty var" { + do_test "" +} + +with_test_prefix "strange named var" { + # In this test we're doing the following: + # + # (gdb) set environment 'asd =' = 123 43; asd b ### [];;; + # + # However, due to how GDB parses this line, the environment + # variable will end up named <'asd> (without the <>), and its + # value will be <' = 123 43; asd b ### [];;;> (without the <>). + do_test "123 43; asd b ### \[\];;;" "'asd ='" "'asd" \ + [string_to_regexp "' = 123 43; asd b ### \[\];;;"] +} + +# Test setting and unsetting environment variables in various +# fashions. + +proc test_set_unset_vars { } { + global binfile + + clean_restart $binfile + + with_test_prefix "set 3 environment variables" { + # Set some environment variables + gdb_test_no_output "set environment A = 1" \ + "set A to 1" + gdb_test_no_output "set environment B = 2" \ + "set B to 2" + gdb_test_no_output "set environment C = 3" \ + "set C to 3" + + do_prepare_inferior + + # Check that the variables are known by the inferior + check_getenv "A" "1" + check_getenv "B" "2" + check_getenv "C" "3" + } + + with_test_prefix "unset one variable, reset one" { + # Now, unset/reset some values + gdb_test_no_output "unset environment A" \ + "unset A" + gdb_test_no_output "set environment B = 4" \ + "set B to 4" + + do_prepare_inferior + + check_getenv "A" "" "" 1 + check_getenv "B" "4" + check_getenv "C" "3" + } + + with_test_prefix "unset two variables, reset one" { + # Unset more values + gdb_test_no_output "unset environment B" \ + "unset B" + gdb_test_no_output "set environment A = 1" \ + "set A to 1 again" + gdb_test_no_output "unset environment C" \ + "unset C" + + do_prepare_inferior + + check_getenv "A" "1" + check_getenv "B" "" "" 1 + check_getenv "C" "" "" 1 + } +} + +with_test_prefix "test set/unset of vars" { + test_set_unset_vars +} + +# Test that unsetting works. + +proc test_unset { } { + global hex decimal binfile gdb_prompt + + clean_restart $binfile + + do_prepare_inferior + + set test_msg "check if unset works" + set found_home 0 + gdb_test_multiple "print my_getenv (\"HOME\")" $test_msg { + -re "\\\$$decimal = $hex \".*\"\r\n$gdb_prompt $" { + pass $test_msg + set found_home 1 + } + -re "\\\$$decimal = 0x0\r\n$gdb_prompt $" { + untested $test_msg + } + } + + if { $found_home == 1 } { + with_test_prefix "simple unset" { + # We can do the test, because $HOME exists (and therefore can + # be unset). + gdb_test_no_output "unset environment HOME" "unset HOME" + + do_prepare_inferior + + # $HOME now must be empty + check_getenv "HOME" "" "" 1 + } + + with_test_prefix "set-then-unset" { + clean_restart $binfile + + # Test if setting and then unsetting $HOME works. + gdb_test_no_output "set environment HOME = test" "set HOME as test" + gdb_test_no_output "unset environment HOME" "unset HOME again" + + do_prepare_inferior + + check_getenv "HOME" "" "" 1 + } + } +} + +with_test_prefix "test unset of vars" { + test_unset +} diff --git a/gdb/testsuite/gdb.base/sizeof.exp b/gdb/testsuite/gdb.base/sizeof.exp index d7ada65..13d36f8 100644 --- a/gdb/testsuite/gdb.base/sizeof.exp +++ b/gdb/testsuite/gdb.base/sizeof.exp @@ -81,12 +81,12 @@ check_sizeof "long double" ${sizeof_long_double} proc check_valueof { exp val } { gdb_test "next" "" "" - gdb_test "p value" " = ${val}" "check valueof \"$exp\"" + gdb_test "p /d value" " = ${val}" "check valueof \"$exp\"" } # Check that GDB and the target agree over the sign of a character. -set signof_byte [get_integer_valueof "'\\377'" -1] +set signof_byte [get_integer_valueof "(int) '\\377'" -1] set signof_char [get_integer_valueof "(int) (char) -1" -1] set signof_signed_char [get_integer_valueof "(int) (signed char) -1" -1] set signof_unsigned_char [get_integer_valueof "(int) (unsigned char) -1" -1] diff --git a/gdb/testsuite/gdb.base/solib-display.exp b/gdb/testsuite/gdb.base/solib-display.exp index 1e26853..6df9f26 100644 --- a/gdb/testsuite/gdb.base/solib-display.exp +++ b/gdb/testsuite/gdb.base/solib-display.exp @@ -94,9 +94,9 @@ foreach libsepdebug {NO IN SEP} { with_test_prefix "$libsepdebug" { return 0 } - gdb_test "display a_global" "1: a_global = 41" - gdb_test "display b_global" "2: b_global = 42" - gdb_test "display c_global" "3: c_global = 43" + gdb_test "display (int) a_global" "1: \\(int\\) a_global = 41" + gdb_test "display (int) b_global" "2: \\(int\\) b_global = 42" + gdb_test "display (int) c_global" "3: \\(int\\) c_global = 43" if { [gdb_start_cmd] < 0 } { fail "can't run to main (2)" @@ -104,9 +104,9 @@ foreach libsepdebug {NO IN SEP} { with_test_prefix "$libsepdebug" { } gdb_test "" [multi_line \ - "1: a_global = 41" \ - "2: b_global = 42" \ - "3: c_global = 43" \ + "1: \\(int\\) a_global = 41" \ + "2: \\(int\\) b_global = 42" \ + "3: \\(int\\) c_global = 43" \ ] "after rerun" # Now rebuild the library without b_global @@ -132,9 +132,9 @@ foreach libsepdebug {NO IN SEP} { with_test_prefix "$libsepdebug" { gdb_test "" [multi_line \ - "1: a_global = 41" \ + "1: \\(int\\) a_global = 41" \ "warning: .*b_global.*" \ - "3: c_global = 43" \ + "3: \\(int\\) c_global = 43" \ ] "after rerun (2)" # Now verify that displays which are not in the shared library diff --git a/gdb/testsuite/gdb.base/starti.c b/gdb/testsuite/gdb.base/starti.c new file mode 100644 index 0000000..f1f359d --- /dev/null +++ b/gdb/testsuite/gdb.base/starti.c @@ -0,0 +1,30 @@ +/* This testcase is part of GDB, the GNU debugger. + + Copyright 2017 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/>. */ + +int x; + +__attribute__((constructor)) void +ctor () +{ + x = 1; +} + +int +main () +{ + return 0; +} diff --git a/gdb/testsuite/gdb.base/starti.exp b/gdb/testsuite/gdb.base/starti.exp new file mode 100644 index 0000000..98167ce --- /dev/null +++ b/gdb/testsuite/gdb.base/starti.exp @@ -0,0 +1,51 @@ +# Copyright 2017 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/>. + + +standard_testfile + +if {[prepare_for_testing "failed to prepare" $testfile $srcfile debug]} { + return -1 +} + +# Define a stop hook that outputs the value of 'x' + +gdb_test_multiple "define hook-stop" "hook-stop" { + -re "Type commands for definition of \"hook-stop\".\r\nEnd with a line saying just \"end\".\r\n>$" { + gdb_test "print x\nend" "" "hook-stop" + } +} + +if { [gdb_starti_cmd] < 0 } { + untested starti + return -1 +} + +# The program should stop at the first instruction, so the constructor +# should not have run yet and 'x' should be 0. + +gdb_test_sequence "" "starti" { + "Program stopped." + "\\$1 = 0" +} + +# Continue to the start of main(). The constructor should have run so +# 'x' should be 1. + +gdb_breakpoint main +gdb_test_sequence "continue" "" { + "\\$2 = 1" + ".*Breakpoint .*main \\(\\) at .*starti.c.*" +} diff --git a/gdb/testsuite/gdb.base/symbol-alias.c b/gdb/testsuite/gdb.base/symbol-alias.c new file mode 100644 index 0000000..cc5d104 --- /dev/null +++ b/gdb/testsuite/gdb.base/symbol-alias.c @@ -0,0 +1,31 @@ +/* This test is part of GDB, the GNU debugger. + + Copyright 2017 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/>. */ + +struct S +{ + int field1; + int field2; +}; + +extern struct S *func_alias (void); + +int +main (void) +{ + struct S *s = func_alias (); + return s->field1 - s->field1; +} diff --git a/gdb/testsuite/gdb.base/symbol-alias.exp b/gdb/testsuite/gdb.base/symbol-alias.exp new file mode 100644 index 0000000..dc63eb1 --- /dev/null +++ b/gdb/testsuite/gdb.base/symbol-alias.exp @@ -0,0 +1,37 @@ +# Test for printing alias symbols. +# Copyright 2017 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/>. + +standard_testfile symbol-alias.c symbol-alias2.c + +if { [prepare_for_testing "failed to prepare" ${testfile} [list $srcfile $srcfile2]] } { + return -1 +} + +if ![runto_main] then { + fail "can't run to main" + continue +} + +# Functions. +foreach f {"func" "func_alias"} { + gdb_test "p $f" " = {struct S \\*\\(void\\)} $hex <func>" + gdb_test "p *${f}()" "= {field1 = 1, field2 = 2}" +} + +# Variables. +foreach v {"g_var_s" "g_var_s_alias"} { + gdb_test "p $v" "= {field1 = 1, field2 = 2}" +} diff --git a/gdb/testsuite/gdb.base/symbol-alias2.c b/gdb/testsuite/gdb.base/symbol-alias2.c new file mode 100644 index 0000000..aedd520 --- /dev/null +++ b/gdb/testsuite/gdb.base/symbol-alias2.c @@ -0,0 +1,34 @@ +/* This test is part of GDB, the GNU debugger. + + Copyright 2017 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/>. */ + +struct S +{ + int field1; + int field2; +}; + +struct S g_var_s = { 1, 2 }; + +static struct S * +func (void) +{ + return &g_var_s; +} + +struct S *func_alias (void) __attribute__ ((alias ("func"))); + +extern struct S g_var_s_alias __attribute__ ((alias ("g_var_s"))); diff --git a/gdb/testsuite/gdb.base/whatis-ptype-typedefs.c b/gdb/testsuite/gdb.base/whatis-ptype-typedefs.c new file mode 100644 index 0000000..5711a96 --- /dev/null +++ b/gdb/testsuite/gdb.base/whatis-ptype-typedefs.c @@ -0,0 +1,143 @@ +/* This test program is part of GDB, the GNU debugger. + + Copyright 2017 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/>. */ + +/* Define typedefs of different types, for testing the "whatis" and + "ptype" commands. */ + +/* Helper macro used to consistently define variables/typedefs using + the same name scheme. BASE is the shared part of the name of all + typedefs/variables generated. Defines a variable of the given + typedef type, and then a typedef of that typedef and a variable of + that new typedef type. The "double typedef" is useful to checking + that whatis only strips one typedef level. For example, if BASE is + "int", we get: + + int_typedef v_int_typedef; // "v_" stands for variable of typedef type + typedef int_typedef int_typedef2; // typedef-of-typedef + int_typedef2 v_int_typedef2; // var of typedef-of-typedef +*/ +#define DEF(base) \ + base ## _typedef v_ ## base ## _typedef; \ + \ + typedef base ## _typedef base ## _typedef2; \ + base ## _typedef2 v_ ## base ## _typedef2 + +/* Void. */ + +/* (Can't have variables of void type.) */ + +typedef void void_typedef; +typedef void_typedef void_typedef2; + +void_typedef *v_void_typedef_ptr; +void_typedef2 *v_void_typedef_ptr2; + +/* Integers. */ + +typedef int int_typedef; +DEF (int); + +/* Floats. */ + +typedef float float_typedef; +DEF (float); + +/* Enums. */ + +typedef enum colors {red, green, blue} colors_typedef; +DEF (colors); + +/* Structures. */ + +typedef struct t_struct +{ + int member; +} t_struct_typedef; +DEF (t_struct); + +/* Unions. */ + +typedef union t_union +{ + int member; +} t_union_typedef; +DEF (t_union); + +/* Arrays. */ + +typedef int int_array_typedef[3]; +DEF (int_array); + +/* An array the same size of t_struct_typedef, so we can test casting. */ +typedef unsigned char uchar_array_t_struct_typedef[sizeof (t_struct_typedef)]; +DEF (uchar_array_t_struct); + +/* A struct and a eunion the same size as t_struct, so we can test + casting. */ + +typedef struct t_struct_wrapper +{ + struct t_struct base; +} t_struct_wrapper_typedef; +DEF (t_struct_wrapper); + +typedef union t_struct_union_wrapper +{ + struct t_struct base; +} t_struct_union_wrapper_typedef; +DEF (t_struct_union_wrapper); + +/* Functions / function pointers. */ + +typedef void func_ftype (void); +func_ftype *v_func_ftype; + +typedef func_ftype func_ftype2; +func_ftype2 *v_func_ftype2; + +/* C++ methods / method pointers. */ + +#ifdef __cplusplus + +namespace ns { + +struct Struct { void method (); }; +void Struct::method () {} + +typedef Struct Struct_typedef; +DEF (Struct); + +/* Typedefs/vars in a namespace. */ +typedef void (Struct::*method_ptr_typedef) (); +DEF (method_ptr); + +} + +/* Similar, but in the global namespace. */ +typedef ns::Struct ns_Struct_typedef; +DEF (ns_Struct); + +typedef void (ns::Struct::*ns_method_ptr_typedef) (); +DEF (ns_method_ptr); + +#endif + +int +main (void) +{ + return 0; +} diff --git a/gdb/testsuite/gdb.base/whatis-ptype-typedefs.exp b/gdb/testsuite/gdb.base/whatis-ptype-typedefs.exp new file mode 100644 index 0000000..d333d81 --- /dev/null +++ b/gdb/testsuite/gdb.base/whatis-ptype-typedefs.exp @@ -0,0 +1,272 @@ +# Copyright 2017 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 "whatis"/"ptype" of different typedef types, and of expressions +# involving casts to/from different typedefs. +# +# Particularly, when "whatis" is given a type name directly, it should +# strip one (and only one) typedef level. Otherwise, it should not +# strip any typedef at all. GDB used to incorrectly strip typedefs of +# expressions involving casts to typedef types. E.g., (gdb) print +# (int_typedef)0" shall result in a value of type "int_typedef", not +# "int". + +standard_testfile + +# Prepare for testing in language LANG. Lang can be "c" or "c++". + +proc prepare {lang} { + global srcfile testfile + + if [target_info exists no_long_long] { + set options [list debug additional_flags=-DNO_LONG_LONG] + } else { + set options [list debug] + } + + if {$lang == "c++"} { + lappend options c++ + set out $testfile-cxx + } else { + set out $testfile-c + } + + if { [prepare_for_testing "failed to prepare" \ + ${out} [list $srcfile] $options] } { + return -1 + } + + if ![runto_main] then { + fail "can't run to main" + return 0 + } +} + +# The following list is layed out as a table. It is composed by +# sub-lists (lines), with each line representing one whatis/ptype +# test. The sub-list (line) elements (columns) are (in order): +# +# EXP - The user expression passed to whatis/ptype. +# +# WHATIS - What "whatis" should print. +# +# If the EXP column is a type name, then this will be the same type, +# with one (and only one) typedef level removed. Otherwise, this is +# the type of the expression on the first column, with all typedefs +# preserved. +# +# PTYPE - What "ptype" should print. +# +# This is always the type of the input type/expression stripped from +# all typedefs. +# +# LANGUAGE - If the line is language-specific, which language. +# +# This can be "c" or "c++". +# +# Columns in the table represent: + # EXP # whatis # ptype # language +set table { + {"void_typedef" "void" "void"} + {"void_typedef2" "void_typedef" "void"} + + {"int_typedef" "int" "int"} + {"int_typedef2" "int_typedef" "int"} + {"v_int_typedef" "int_typedef" "int"} + {"v_int_typedef2" "int_typedef2" "int"} + + {"float_typedef" "float" "float"} + {"float_typedef2" "float_typedef" "float"} + {"v_float_typedef" "float_typedef" "float"} + {"v_float_typedef2" "float_typedef2" "float"} + + {"colors_typedef" "(enum )?colors" "enum colors( : unsigned int)? {red, green, blue}"} + {"colors_typedef2" "colors_typedef" "enum colors( : unsigned int)? {red, green, blue}"} + {"v_colors_typedef" "colors_typedef" "enum colors( : unsigned int)? {red, green, blue}"} + {"v_colors_typedef2" "colors_typedef2" "enum colors( : unsigned int)? {red, green, blue}"} + + {"func_ftype" "void \\(void\\)" "void \\(void\\)"} + {"func_ftype2" "func_ftype" "void \\(void\\)"} + + {"func_ftype *" "func_ftype \\*" "void \\(\\*\\)\\(void\\)"} + {"func_ftype2 *" "func_ftype2 \\*" "void \\(\\*\\)\\(void\\)"} + {"v_func_ftype" "func_ftype \\*" "void \\(\\*\\)\\(void\\)"} + {"v_func_ftype2" "func_ftype2 \\*" "void \\(\\*\\)\\(void\\)"} + + {"v_t_struct_typedef" "t_struct_typedef" "struct t_struct {.* member;.*}"} + {"v_t_struct_typedef2" "t_struct_typedef2" "struct t_struct {.* member;.*}"} + {"v_t_struct_union_wrapper_typedef" "t_struct_union_wrapper_typedef" "union t_struct_union_wrapper {.*base;.*}"} + {"v_t_struct_union_wrapper_typedef2" "t_struct_union_wrapper_typedef2" "union t_struct_union_wrapper {.*base;.*}"} + {"v_uchar_array_t_struct_typedef" "uchar_array_t_struct_typedef" "unsigned char \\[.*\\]"} + {"v_uchar_array_t_struct_typedef2" "uchar_array_t_struct_typedef2" "unsigned char \\[.*\\]"} + + {"v_ns_Struct_typedef" "ns_Struct_typedef" "struct ns::Struct {.* method.*}" "c++"} + + {"ns_method_ptr_typedef" + "void \\(ns::Struct::\\*\\)\\(ns::Struct \\* const\\)" + "void \\(ns::Struct::\\*\\)\\(ns::Struct \\* const\\)" + "c++"} + + {"ns::method_ptr_typedef" + "void \\(ns::Struct::\\*\\)\\(ns::Struct \\* const\\)" + "void \\(ns::Struct::\\*\\)\\(ns::Struct \\* const\\)" + "c++"} + + {"ns_method_ptr_typedef2" + "ns_method_ptr_typedef" + "void \\(ns::Struct::\\*\\)\\(ns::Struct \\* const\\)" + "c++"} + + {"ns::method_ptr_typedef2" + "ns::method_ptr_typedef" + "void \\(ns::Struct::\\*\\)\\(ns::Struct \\* const\\)" + "c++"} + + {"ns::Struct::method" + "void \\(ns::Struct \\* const\\)" + "void \\(ns::Struct \\* const\\)" + "c++"} +} + +# The 4th column above is optional. If present, it indicates that the +# line should only be tested in the specified language. This is a +# helper function that checks whether LINE's language matches LANG. +proc line_lang_match {line lang} { + if {[llength $line] <= 3} { + return true + } + + set line_lang [lindex $line 3] + if {$line_lang == "" || $lang == $line_lang} { + return true + } + + return false +} + +# Run tests in language LANG. + +proc run_tests {lang} { + global table + global gdb_prompt + + # Test passing all EXP in the list/table above to whatis/ptype, + # and check what comes out. + with_test_prefix "whatis/ptype" { + foreach line $table { + set type [lindex $line 0] + set whatis [lindex $line 1] + set ptype [lindex $line 2] + + if {![line_lang_match $line $lang]} { + continue + } + + # GCC doesn't record the target type of "typedef of + # typedef of void" types in the DWARF. See + # <https://gcc.gnu.org/bugzilla/show_bug.cgi?id=81267>. + # Handle that case manually in order to be able to xfail + # it. + if {$type == "void_typedef2"} { + set test "whatis $type" + gdb_test_multiple $test $test { + -re "type = void\r\n$gdb_prompt $" { + # gcc/81267. + setup_xfail "*-*-*" + fail "$test (void)" + } + -re "type = void_typedef\r\n$gdb_prompt $" { + pass $test + } + } + } else { + gdb_test "whatis $type" "type = $whatis" + } + + gdb_test "ptype $type" "type = $ptype" + } + } + + # Test converting/casting all variables in the first column of the + # table to all types (found in the first column of the table). + # The aggregates are all defined to be the same size so that + # casting actually works. (GDB's casting operator is more general + # than a C cast.) + # + # The main idea here is testing all the different paths in the + # value casting code in GDB (value_cast), making sure typedefs are + # preserved. + with_test_prefix "cast" { + foreach line1 $table { + set from [lindex $line1 0] + + if {![line_lang_match $line1 $lang]} { + continue + } + + foreach line2 $table { + set to [lindex $line2 0] + set whatis [lindex $line2 1] + set ptype [lindex $line2 2] + + if {![line_lang_match $line2 $lang]} { + continue + } + + # We try all combinations, even those that don't + # parse, or are invalid, to catch the case of a + # regression making them inadvertently valid. For + # example, these convertions are invalid: + # + # float <-> array + # array -> function (not function pointer) + # array -> member_ptr + # + # while these are invalid syntax: + # + # (anything) type + # (var) anything + # (method) anything [not method pointer] + # (float) method + # + if {([string match "v_*" $to] + || (![string match "v_*" $from] && ![string match "*method" $from]) + || [string match "*method" $to])} { + gdb_test "whatis ($to) $from" "syntax error.*" "whatis ($to) $from (syntax)" + gdb_test "ptype ($to) $from" "syntax error.*" "ptype ($to) $from (syntax)" + } elseif {([string match "*float*" $from] && [string match "*array*" $to]) + || ([string match "float*" $to] && [string match "*array*" $from]) + || ([string match "float*" $to] && [string match "*method" $from]) + || ([string match "*ftype" $to] && [string match "*array*" $from]) + || ([string match "*ftype2" $to] && [string match "*array*" $from]) + || ([string match "*ftype" $to] && [string match "*method" $from]) + || ([string match "*ftype2" $to] && [string match "*method" $from]) + || ([string match "*method_ptr*" $to] && [string match "*method" $from]) + || ([string match "*method_ptr*" $to] && [string match "*array*" $from])} { + gdb_test "whatis ($to) $from" "Invalid cast." "whatis ($to) $from (invalid)" + gdb_test "ptype ($to) $from" "Invalid cast." "ptype ($to) $from (invalid)" + } else { + gdb_test "whatis ($to) $from" "type = [string_to_regexp $to]" + gdb_test "ptype ($to) $from" "type = $ptype" + } + } + } + } +} + +foreach_with_prefix lang {"c" "c++"} { + prepare $lang + run_tests $lang +} |