Star wildcard ranges (e.g., "info thread 2.*")
[external/binutils.git] / gdb / testsuite / gdb.multi / tids.exp
1 # Copyright 2015-2016 Free Software Foundation, Inc.
2
3 # This program is free software; you can redistribute it and/or modify
4 # it under the terms of the GNU General Public License as published by
5 # the Free Software Foundation; either version 3 of the License, or
6 # (at your option) any later version.
7 #
8 # This program is distributed in the hope that it will be useful,
9 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 # GNU General Public License for more details.
12 #
13 # You should have received a copy of the GNU General Public License
14 # along with this program.  If not, see <http://www.gnu.org/licenses/>.
15
16 # Test thread ID parsing and display.
17
18 load_lib gdb-python.exp
19
20 standard_testfile
21
22 # Multiple inferiors are needed, therefore both native and extended
23 # gdbserver modes are supported.  Only non-extended gdbserver is not
24 # supported.
25 if [target_info exists use_gdb_stub] {
26     untested ${testfile}.exp
27     return
28 }
29
30 if { [prepare_for_testing "failed to prepare" ${testfile} ${srcfile} {pthreads debug}] } {
31     return -1
32 }
33
34 clean_restart ${testfile}
35
36 if { ![runto_main] } then {
37     return -1
38 }
39
40 # Issue "thread apply TID_LIST p 1234" and expect EXP_TID_LIST (a list
41 # of thread ids) to be displayed.
42 proc thread_apply {tid_list exp_tid_list {message ""}} {
43     global decimal
44     set any "\[^\r\n\]*"
45     set expected [string_to_regexp $exp_tid_list]
46
47     set r ""
48     foreach tid $expected {
49         append r "\[\r\n\]+"
50         append r "Thread $tid $any:\r\n"
51         append r "\\$$decimal = 1234"
52     }
53
54     set cmd "thread apply $tid_list"
55     if {$message == ""} {
56         set message $cmd
57     }
58     gdb_test "$cmd p 1234" $r $message
59 }
60
61 # Issue "info threads TID_LIST" and expect EXP_TID_LIST (a list of
62 # thread ids) to be displayed.
63 proc info_threads {tid_list exp_tid_list {message ""}} {
64     set any "\[^\r\n\]*"
65     set expected [string_to_regexp $exp_tid_list]
66     set r [join $expected " ${any}\r\n${any} "]
67     set r "${any} $r ${any}"
68     set cmd "info threads $tid_list"
69     if {$message == ""} {
70         set message $cmd
71     }
72     gdb_test $cmd $r $message
73 }
74
75 # Issue "info threads TID_LIST" and expect INFO_THR output.  Then
76 # issue "thread apply TID_LIST" and expect THR_APPLY output.  If
77 # THR_APPLY is omitted, INFO_THR is expected instead.
78 proc thr_apply_info_thr {tid_list info_thr {thr_apply ""}} {
79     if {$thr_apply == ""} {
80         set thr_apply $info_thr
81     }
82
83     info_threads $tid_list $info_thr
84     thread_apply $tid_list $thr_apply
85 }
86
87 # Issue both "info threads TID_LIST" and "thread apply TID_LIST" and
88 # expect both commands to error out with EXP_ERROR.
89 proc thr_apply_info_thr_error {tid_list exp_error}  {
90     gdb_test "info threads $tid_list" \
91         $exp_error
92
93     gdb_test "thread apply $tid_list" \
94         $exp_error \
95         "thread apply $tid_list"
96 }
97
98 # Issue both "info threads TID_LIST" and "thread apply TID_LIST" and
99 # expect the command to error out with "Invalid thread ID: $EXPECTED".
100 # EXPECTED is a literal string, not a regexp.  If EXPECTED is omitted,
101 # TID_LIST is expected instead.
102 proc thr_apply_info_thr_invalid {tid_list {expected ""}} {
103     if {$expected == ""} {
104         set expected $tid_list
105     }
106     set expected [string_to_regexp $expected]
107     gdb_test "info threads $tid_list" \
108         "Invalid thread ID: $expected"
109
110     gdb_test "thread apply $tid_list p 1234" \
111         "Invalid thread ID: $expected p 1234" \
112         "thread apply $tid_list"
113 }
114
115 # "info threads" while there's only inferior 1 should show
116 # single-number thread IDs.
117 with_test_prefix "single inferior" {
118     info_threads "" "1"
119
120     gdb_test "thread" "Current thread is 1 .*"
121 }
122
123 # "info threads" while there are multiple inferiors should show
124 # qualified thread IDs.
125 with_test_prefix "two inferiors" {
126     # Add another inferior.
127     gdb_test "add-inferior" "Added inferior 2.*" "add empty inferior 2"
128
129     # Now that we've added another inferior, thread IDs now show the
130     # inferior number.
131     info_threads "" "1.1"
132
133     gdb_test "thread" "Current thread is 1\.1 .*"
134
135     gdb_test "inferior 2" "Switching to inferior 2 .*" "switch to inferior 2"
136     gdb_test "file ${binfile}" ".*" "load file in inferior 2"
137
138     runto_main
139
140     # Now that we've added another inferior, thread IDs now show the
141     # inferior number.
142     info_threads "" "1.1 2.1" \
143         "info threads show inferior numbers"
144
145     gdb_test "thread" "Current thread is 2\.1 .*" \
146         "switch to thread using extended thread ID"
147
148     gdb_breakpoint "thread_function1"
149
150     gdb_continue_to_breakpoint "once"
151     gdb_test "inferior 1" "Switching to inferior 1 .*"
152     gdb_continue_to_breakpoint "twice"
153
154     info_threads "" "1.1 1.2 2.1 2.2" \
155         "info threads again"
156
157     # Same, but show the global ID.
158     gdb_test "info threads -gid" \
159         [multi_line \
160              "  1\.1 +1 +.*" \
161              "\\* 1\.2 +4 +.* thread_function1 .* at .*$srcfile:.*" \
162              "  2\.1 +2 +.*" \
163              "  2\.2 +3 +.* thread_function1 .* at .*$srcfile:.*"]
164
165     # Confirm the convenience variables show the expected numbers.
166     gdb_test "p \$_thread == 2" " = 1"
167     gdb_test "p \$_gthread == 4" " = 1"
168
169     # Without an explicit inferior component, GDB defaults to the
170     # current inferior.  Make sure we don't refer to a thread by
171     # global ID by mistake.
172     gdb_test "thread 4" "Unknown thread 1.4\\."
173
174     # Test thread ID list parsing.  Test qualified and unqualified
175     # IDs; qualified and unqualified ranges; invalid IDs and invalid
176     # ranges.
177
178     # First spawn a couple more threads so ranges includes more than
179     # two threads.
180     with_test_prefix "more threads" {
181         gdb_breakpoint "thread_function2"
182
183         gdb_test "inferior 2" "Switching to inferior 2 .*"
184         gdb_continue_to_breakpoint "once"
185
186         gdb_test "inferior 1" "Switching to inferior 1 .*"
187         gdb_continue_to_breakpoint "twice"
188     }
189
190     thr_apply_info_thr "1" \
191         "1.1"
192
193     thr_apply_info_thr "1.1" \
194         "1.1"
195
196     thr_apply_info_thr "1 2 3" \
197         "1.1 1.2 1.3"
198
199     # Same, but with qualified thread IDs.
200     thr_apply_info_thr "1.1 1.2 1.3 2.1 2.2" \
201         "1.1 1.2 1.3 2.1 2.2"
202
203     # Test a thread number range.
204     thr_apply_info_thr "1-3" \
205         "1.1 1.2 1.3"
206
207     # Same, but using a qualified range.
208     thr_apply_info_thr "1.1-3" \
209         "1.1 1.2 1.3"
210
211     # A mix of qualified and unqualified thread IDs/ranges.
212     thr_apply_info_thr "1.1 2-3" \
213         "1.1 1.2 1.3"
214
215     thr_apply_info_thr "1 1.2-3" \
216         "1.1 1.2 1.3"
217
218     # Likewise, but mix inferiors too.
219     thr_apply_info_thr "2.1 2-3" \
220         "1.2 1.3 2.1" \
221         "2.1 1.2 1.3"
222
223     # Multiple ranges with mixed explicit inferiors.
224     thr_apply_info_thr "1.1-2 2.2-3" \
225         "1.1 1.2 2.2 2.3"
226
227     # Now test using GDB convenience variables.
228
229     gdb_test "p \$inf = 1" " = 1"
230     gdb_test "p \$thr_start = 2" " = 2"
231     gdb_test "p \$thr_end = 3" " = 3"
232
233     # Convenience variable for the inferior number, only.
234     thr_apply_info_thr "\$inf.2" \
235         "1.2"
236     thr_apply_info_thr "\$inf.2-3" \
237         "1.2 1.3"
238
239     # Convenience variables for thread numbers as well.
240     foreach prefix {"" "1." "\$inf."} {
241         thr_apply_info_thr "${prefix}\$thr_start" \
242             "1.2"
243         thr_apply_info_thr "${prefix}\$thr_start-\$thr_end" \
244             "1.2 1.3"
245         thr_apply_info_thr "${prefix}2-\$thr_end" \
246             "1.2 1.3"
247         thr_apply_info_thr "${prefix}\$thr_start-3" \
248             "1.2 1.3"
249
250         # Undefined convenience variable.
251         set prefix_re [string_to_regexp $prefix]
252         thr_apply_info_thr_error "${prefix}\$conv123" \
253             [multi_line \
254                  "Convenience variable must have integer value\." \
255                  "Invalid thread ID: ${prefix_re}\\\$conv123"]
256     }
257
258     # Convenience variables pointing at an inexisting thread and/or
259     # inferior.
260     gdb_test "p \$inf = 30" " = 30"
261     gdb_test "p \$thr = 20" " = 20"
262     # Try both the convenience variable and the literal number.
263     foreach thr {"\$thr" "20" "1.20" "\$inf.1" "30.1" } {
264         set expected [string_to_regexp $thr]
265         gdb_test "info threads $thr" "No threads match '${expected}'."
266         # "info threads" works like a filter.  If there's any other
267         # valid thread in the list, there's no error.
268         info_threads "$thr 1.1" "1.1"
269         info_threads "1.1 $thr" "1.1"
270     }
271
272     gdb_test "thread apply \$thr p 1234" \
273         "warning: Unknown thread 1.20" \
274         "thread apply \$thr"
275
276     gdb_test "thread apply \$inf.1 p 1234" \
277         "warning: Unknown thread 30.1" \
278         "thread apply \$inf.1"
279
280     # Star ranges.
281
282     thr_apply_info_thr "1.*" \
283         "1.1 1.2 1.3"
284
285     thr_apply_info_thr "*" \
286         "1.1 1.2 1.3"
287
288     thr_apply_info_thr "1.* 2.1" \
289         "1.1 1.2 1.3 2.1"
290
291     thr_apply_info_thr "2.1 1.*" \
292         "1.1 1.2 1.3 2.1" \
293         "2.1 1.1 1.2 1.3"
294
295     thr_apply_info_thr "1.* 2.*" \
296         "1.1 1.2 1.3 2.1 2.2 2.3"
297
298     thr_apply_info_thr "2.* 1.*" \
299         "1.1 1.2 1.3 2.1 2.2 2.3" \
300         "2.1 2.2 2.3 1.1 1.2 1.3"
301
302     # There's no inferior 3, but "info threads" treats the thread list
303     # as a filter, so it's OK.  "thread apply" complains about the
304     # unknown inferior through.
305     info_threads "1.1 3.*" \
306         "1.1"
307     gdb_test "thread apply 1.1 3.* p 1" \
308         "Thread 1.1.*warning: Unknown inferior 3"
309
310     # Now test a set of invalid thread IDs/ranges.
311
312     thr_apply_info_thr_invalid "1." \
313         "1."
314
315     thr_apply_info_thr_invalid "1-3 1." \
316         "1."
317
318     thr_apply_info_thr_invalid "1.1.1" \
319         "1.1.1"
320
321     thr_apply_info_thr_invalid "2 1.1.1" \
322         "1.1.1"
323
324     thr_apply_info_thr_invalid "1.1.1 2" \
325         "1.1.1 2"
326
327     thr_apply_info_thr_invalid "1-2.1" \
328         "1-2.1"
329
330     gdb_test "p \$zero = 0" " = 0"
331     gdb_test "p \$one = 1" " = 1"
332     gdb_test "p \$minus_one = -11" " = -11"
333     foreach prefix {"" "1." "$one."} {
334         set prefix_re [string_to_regexp $prefix]
335
336         thr_apply_info_thr_invalid "${prefix}foo"
337         thr_apply_info_thr_invalid "${prefix}1foo"
338         thr_apply_info_thr_invalid "${prefix}foo1"
339
340         thr_apply_info_thr_error "${prefix}1-0" "inverted range"
341         thr_apply_info_thr_error "${prefix}1-\$zero" "inverted range"
342         thr_apply_info_thr_error "${prefix}\$one-0" "inverted range"
343         thr_apply_info_thr_error "${prefix}\$one-\$zero" "inverted range"
344         thr_apply_info_thr_error "${prefix}1-" "inverted range"
345         thr_apply_info_thr_error "${prefix}2-1" "inverted range"
346         thr_apply_info_thr_error "${prefix}2-\$one" "inverted range"
347         thr_apply_info_thr_error "${prefix}-1" "negative value"
348         thr_apply_info_thr_error "${prefix}-\$one" "negative value"
349         thr_apply_info_thr_error "${prefix}\$minus_one" \
350             "negative value: ${prefix_re}\\\$minus_one"
351
352         thr_apply_info_thr_error "${prefix}1-*" "inverted range"
353         thr_apply_info_thr_invalid "${prefix}*1"
354         thr_apply_info_thr_invalid "${prefix}*foo"
355         thr_apply_info_thr_invalid "${prefix}foo*"
356     }
357
358     # Check that a valid thread ID list with a missing command errors
359     # out.
360     with_test_prefix "missing command" {
361         set output "Please specify a command following the thread ID list"
362         gdb_test "thread apply 1" $output
363         gdb_test "thread apply 1.1" $output
364         gdb_test "thread apply 1.1 1.2" $output
365         gdb_test "thread apply 1-2" $output
366         gdb_test "thread apply 1.1-2" $output
367         gdb_test "thread apply $thr" $output
368         gdb_test "thread apply 1.*" $output
369     }
370
371     # Check that we do parse the inferior number and don't confuse it.
372     gdb_test "info threads 3.1" \
373         "No threads match '3.1'\."
374 }
375
376 if { ![skip_python_tests] } {
377     with_test_prefix "python" {
378         # Check that InferiorThread.num and InferiorThread.global_num
379         # return the expected numbers.
380         gdb_py_test_silent_cmd "python t0 = gdb.selected_thread ()" \
381             "test gdb.selected_thread" 1
382         gdb_test "python print ('result = %s' % t0.num)" " = 3" \
383             "test InferiorThread.num"
384         gdb_test "python print ('result = %s' % t0.global_num)" " = 6" \
385             "test InferiorThread.global_num"
386
387         # Breakpoint.thread expects global IDs.  Confirm that that
388         # works as expected.
389         delete_breakpoints
390         gdb_breakpoint "thread_function1"
391
392         gdb_py_test_silent_cmd "python bp = gdb.breakpoints()\[0\]" \
393             "get python breakpoint" 0
394         gdb_test "python bp.thread = 6" "thread = 6" \
395             "make breakpoint thread-specific with python"
396         # Check that the inferior-qualified ID is correct.
397         gdb_test "info breakpoint" \
398             "stop only in thread 1.3\r\n.*" \
399             "thread specific breakpoint right thread"
400     }
401 }
402
403 # Remove the second inferior and confirm that GDB goes back to showing
404 # single-number thread IDs.
405 with_test_prefix "back to one inferior" {
406     gdb_test "kill inferior 2" "" "kill inferior 2" "Kill the program being debugged.*" "y"
407     gdb_test "thread 1.1" "Switching to thread 1\.1 .*"
408     gdb_test "remove-inferior 2" ".*" "remove inferior 2"
409
410     # "info threads" while there's only inferior 1 should show
411     # single-number thread IDs.
412     info_threads "" "1 2 3"
413
414     gdb_test "thread" "Current thread is 1 .*"
415 }
416
417 # Add another inferior and remove inferior 1.  Since even though
418 # there's a single inferior, its number is not 1, GDB should show
419 # inferior-qualified thread IDs.
420 with_test_prefix "single-inferior but not initial" {
421     # Add another inferior.
422     gdb_test "add-inferior" "Added inferior 3.*" "add empty inferior"
423
424     # Now that we'd added another inferior, thread IDs should show the
425     # inferior number.
426     info_threads "" "1.1 1.2 1.3" \
427         "info threads with multiple inferiors"
428
429     gdb_test "thread" "Current thread is 1\.1 .*"
430
431     gdb_test "inferior 3" "Switching to inferior 3 .*" "switch to inferior 3"
432     gdb_test "file ${binfile}" ".*" "load file in inferior 3"
433
434     runto_main
435
436     gdb_test "remove-inferior 1" ".*" "remove inferior 1"
437
438     # Even though we have a single inferior, its number is > 1, so
439     # thread IDs should include the inferior number.
440     info_threads "" "3.1" \
441         "info threads with single inferior"
442
443     gdb_test "thread" "Current thread is 3\.1 .*" "thread again"
444 }