Support R_SPARC_WDISP10 and R_SPARC_H34.
[external/binutils.git] / gdb / testsuite / gdb.base / foll-vfork.exp
1 #   Copyright 1997, 1999, 2007-2012 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 if { [is_remote target] || ![isnative] } then {
17     continue
18 }
19
20
21 # NOTE drow/2002-12-06: I don't know what the referenced kernel problem
22 # is, but it appears to be fixed in recent HP/UX versions.
23
24 ##if [istarget "hppa2.0w-hp-hpux*"] {
25 ##  warning "Don't run gdb.base/foll-vfork.exp until JAGaa43495 kernel problem is fixed."
26 ##  return 0
27 ##}
28
29 global srcfile
30 set testfile "foll-vfork"
31 set testfile2 "vforked-prog"
32 set srcfile ${testfile}.c
33 set srcfile2 ${testfile2}.c
34 set binfile ${objdir}/${subdir}/${testfile}
35 set binfile2 ${objdir}/${subdir}/${testfile2}
36
37 if  { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug}] != "" } {
38      untested foll-vfork.exp
39      return -1
40 }
41
42 if  { [gdb_compile "${srcdir}/${subdir}/${srcfile2}" "${binfile2}" executable {debug}] != "" } {
43      untested foll-vfork.exp
44      return -1
45 }
46
47
48 # Until "set follow-fork-mode" and "catch vfork" are implemented on
49 # other targets...
50 #
51 if {![istarget "hppa*-hp-hpux*"] && ![istarget "*-linux*"]} then {
52     continue
53 }
54
55 # Test to see if we are on an HP-UX 10.20 and if so,
56 # do not run these tests as catching vfork is disabled for
57 # 10.20.
58
59 if [istarget "hppa*-hp-hpux10.20"] then {
60     return 0
61 }
62
63 # A few of these tests require a little more time than the standard
64 # timeout allows.
65 set oldtimeout $timeout
66 set timeout [expr "$timeout + 10"]
67
68 proc check_vfork_catchpoints {} {
69   global gdb_prompt
70   global has_vfork_catchpoints
71
72   # Verify that the system supports "catch vfork".
73   gdb_test "catch vfork" "Catchpoint \[0-9\]* \\(vfork\\)" "insert first vfork catchpoint"
74   set has_vfork_catchpoints 0
75   gdb_test_multiple "continue" "continue to first vfork catchpoint" {
76     -re ".*Your system does not support this type\r\nof catchpoint.*$gdb_prompt $" {
77       unsupported "continue to first vfork catchpoint"
78     }
79     -re ".*Catchpoint.*$gdb_prompt $" {
80       set has_vfork_catchpoints 1
81       pass "continue to first vfork catchpoint"
82     }
83   }
84
85   if {$has_vfork_catchpoints == 0} {
86     unsupported "vfork catchpoints"
87     return -code return
88   }
89 }
90
91 proc vfork_parent_follow_through_step {} {
92    global gdb_prompt
93
94    send_gdb "set follow-fork parent\n"
95    gdb_expect {
96       -re "$gdb_prompt $" {pass "set follow-fork parent, vfork through step"}
97       timeout         {fail "set follow-fork parent, vfork through step"}
98    }
99    send_gdb "next\n"
100    gdb_expect {
101       -re "Detaching after fork from.*13.*$gdb_prompt "\
102                       {pass "vfork parent follow, through step"}
103       -re "$gdb_prompt $" {fail "vfork parent follow, through step"}
104       timeout         {fail "(timeout) vfork parent follow, through step" }
105    }
106    # The child has been detached; allow time for any output it might
107    # generate to arrive, so that output doesn't get confused with
108    # any gdb_expected debugger output from a subsequent testpoint.
109    #
110    exec sleep 1
111 }
112
113 proc vfork_parent_follow_to_bp {} {
114    global gdb_prompt
115    global srcfile
116
117    send_gdb "set follow-fork parent\n"
118    gdb_expect {
119       -re "$gdb_prompt $" {pass "set follow-fork parent, vfork to bp"}
120       timeout         {fail "set follow-fork parent, vfork to bp"}
121    }
122    send_gdb "break ${srcfile}:18\n"
123    gdb_expect {
124       -re "$gdb_prompt $" {pass "break, vfork to bp"}
125       timeout         {fail "break, vfork to bp"}
126    }
127    send_gdb "continue\n"
128    gdb_expect {
129       -re ".*Detaching after fork from child process.*Breakpoint.*18.*$gdb_prompt "\
130                       {pass "vfork parent follow, to bp"}
131       -re "$gdb_prompt $" {fail "vfork parent follow, to bp"}
132       timeout         {fail "(timeout) vfork parent follow, to bp" }
133    }
134    # The child has been detached; allow time for any output it might
135    # generate to arrive, so that output doesn't get confused with
136    # any expected debugger output from a subsequent testpoint.
137    #
138    exec sleep 1
139 }
140
141 proc vfork_and_exec_child_follow_to_main_bp {} {
142    global gdb_prompt
143    global binfile
144
145    send_gdb "set follow-fork child\n"
146    gdb_expect {
147       -re "$gdb_prompt $" {pass "set follow-fork child, vfork and exec to main bp"}
148       timeout         {fail "set follow-fork child, vfork and exec to main bp"}
149    }
150    send_gdb "continue\n"
151    gdb_expect {
152       -re "Attaching after.* vfork to.*xecuting new program.*Breakpoint.*vforked-prog.c:9.*$gdb_prompt "\
153                       {pass "vfork and exec child follow, to main bp"}
154       -re "$gdb_prompt $" {fail "vfork and exec child follow, to main bp"}
155       timeout         {fail "(timeout) vfork and exec child follow, to main bp" }
156    }
157    # The parent has been detached; allow time for any output it might
158    # generate to arrive, so that output doesn't get confused with
159    # any gdb_expected debugger output from a subsequent testpoint.
160    #
161    exec sleep 1
162
163    # Explicitly kill this child, or a subsequent rerun actually runs
164    # the exec'd child, not the original program...
165    send_gdb "kill\n"
166    gdb_expect {
167       -re ".*Kill the program being debugged.*y or n. $" {
168          gdb_test_no_output "y" ""
169          send_gdb "file $binfile\n"
170          gdb_expect {
171             -re ".*Load new symbol table from.*y or n. $" {
172                send_gdb "y\n"
173                gdb_expect {
174                   -re "Reading symbols from.*$gdb_prompt $" {}
175                   timeout { fail "loading symbols (timeout)"; return }
176                }
177             }
178             -re ".*gdb_prompt $" {}
179             timeout { fail "loading symbols (timeout)"; return }
180           }
181       }
182       -re ".*$gdb_prompt $" {}
183       timeout { fail "killing inferior (timeout)" ; return }
184     }
185 }
186
187 proc vfork_and_exec_child_follow_through_step {} {
188    global gdb_prompt
189    global binfile
190
191 # This test cannot be performed prior to HP-UX 10.30, because ptrace-based
192 # debugging of a vforking program basically doesn't allow the child to do
193 # things like hit a breakpoint between a vfork and exec.  This means that
194 # saying "set follow-fork child; next" at a vfork() call won't work, because
195 # the implementation of "next" sets a "step resume" breakpoint at the
196 # return from the vfork(), which the child will hit on its way to exec'ing.
197 #
198    if { ![istarget "hppa*-*-hpux11.*"] } {
199       verbose "vfork child-following next test ignored for non-hppa or pre-HP/UX-10.30 targets."
200       return 0
201    }
202
203    send_gdb "set follow-fork child\n"
204    gdb_expect {
205       -re "$gdb_prompt $" {pass "set follow-fork child, vfork and exec through step"}
206       timeout         {fail "set follow-fork child, vfork and exec through step"}
207    }
208    send_gdb "next\n"
209    gdb_expect {
210       -re "Attaching after fork to.*Executing new program.*Breakpoint.*vforked-prog.c:9.*$gdb_prompt "\
211                       {pass "vfork and exec child follow, through step"}
212       -re "$gdb_prompt $" {fail "vfork and exec child follow, through step"}
213       timeout         {fail "(timeout) vfork and exec child follow, through step" }
214    }
215    # The parent has been detached; allow time for any output it might
216    # generate to arrive, so that output doesn't get confused with
217    # any expected debugger output from a subsequent testpoint.
218    #
219    exec sleep 1
220
221    # Explicitly kill this child, or a subsequent rerun actually runs
222    # the exec'd child, not the original program...
223    send_gdb "kill\n"
224    gdb_expect {
225       -re ".*Kill the program being debugged.*y or n. $" {
226          gdb_test_no_output "y" ""
227          send_gdb "file $binfile\n"
228          gdb_expect {
229             -re ".*Load new symbol table from.*y or n. $" {
230                send_gdb "y\n"
231                gdb_expect {
232                   -re "Reading symbols from.*$gdb_prompt $" {}
233                   timeout { fail "loading symbols (timeout)"; return }
234                }
235             }
236             -re ".*gdb_prompt $" {}
237             timeout { fail "loading symbols (timeout)"; return }
238           }
239       }
240       -re ".*$gdb_prompt $" {}
241       timeout { fail "killing inferior (timeout)" ; return }
242     }
243 }
244
245 proc tcatch_vfork_then_parent_follow {} {
246    global gdb_prompt
247    global srcfile
248
249    send_gdb "set follow-fork parent\n"
250    gdb_expect {
251       -re "$gdb_prompt $" {pass "set follow-fork parent, tcatch vfork"}
252       timeout         {fail "set follow-fork parent, tcatch vfork"}
253    }
254    send_gdb "tcatch vfork\n"
255    gdb_expect {
256       -re "Catchpoint .*(vfork).*$gdb_prompt $"\
257                       {pass "vfork parent follow, set tcatch vfork"}
258       -re "$gdb_prompt $" {fail "vfork parent follow, set tcatch vfork"}
259       timeout         {fail "(timeout) vfork parent follow, set tcatch vfork"}
260    }
261    send_gdb "continue\n"
262 # HP-UX 10.20 seems to stop you in "vfork", while more recent HP-UXs
263 # stop you in "_vfork".
264    gdb_expect {
265       -re "0x\[0-9a-fA-F\]*.*(vfork|__kernel_v?syscall).*$gdb_prompt "\
266                       {pass "vfork parent follow, tcatch vfork"}
267       -re "vfork \\(\\) at.*$gdb_prompt "\
268                       {pass "vfork parent follow, tcatch vfork"}
269       -re "$gdb_prompt $" {fail "vfork parent follow, tcatch vfork"}
270       timeout         {fail "(timeout) vfork parent follow, tcatch vfork"}
271    }
272    send_gdb "finish\n"
273    gdb_expect {
274       -re "Run till exit from.*vfork.*0x\[0-9a-fA-F\]* in main .* at .*${srcfile}:12.*$gdb_prompt "\
275                       {pass "vfork parent follow, finish after tcatch vfork"}
276       -re "Run till exit from.*__kernel_v?syscall.*0x\[0-9a-fA-F\]* in vfork .*$gdb_prompt " {
277           send_gdb "finish\n"
278           exp_continue
279       }
280       -re "$gdb_prompt $" {fail "vfork parent follow, finish after tcatch vfork"}
281       timeout         {fail "(timeout) vfork parent follow, finish after tcatch vfork" }
282    }
283    # The child has been detached; allow time for any output it might
284    # generate to arrive, so that output doesn't get confused with
285    # any expected debugger output from a subsequent testpoint.
286    #
287    exec sleep 1
288 }
289
290 proc tcatch_vfork_then_child_follow {} {
291    global gdb_prompt
292    global srcfile
293    global srcfile2
294
295    send_gdb "set follow-fork child\n"
296    gdb_expect {
297       -re "$gdb_prompt $" {pass "set follow-fork child, tcatch vfork"}
298       timeout         {fail "set follow-fork child, tcatch vfork"}
299    }
300    send_gdb "tcatch vfork\n"
301    gdb_expect {
302       -re "Catchpoint .*(vfork).*$gdb_prompt $"\
303                       {pass "vfork child follow, set tcatch vfork"}
304       -re "$gdb_prompt $" {fail "vfork child follow, set tcatch vfork"}
305       timeout         {fail "(timeout) vfork child follow, set tcatch vfork"}
306    }
307    send_gdb "continue\n"
308 # HP-UX 10.20 seems to stop you in "vfork", while more recent HP-UXs
309 # stop you in "_vfork".
310    gdb_expect {
311       -re "vfork \\(\\) at .*$gdb_prompt $"\
312                       {pass "vfork child follow, tcatch vfork"}
313       -re "0x\[0-9a-fA-F\]*.*(vfork|__kernel_v?syscall).*$gdb_prompt "\
314                       {pass "vfork child follow, tcatch vfork"}
315       -re "$gdb_prompt $" {fail "vfork child follow, tcatch vfork"}
316       timeout         {fail "(timeout) vfork child follow, tcatch vfork"}
317    }
318    send_gdb "finish\n"
319    gdb_expect {
320       -re "Run till exit from.*vfork.*${srcfile}:12.*$gdb_prompt "\
321                       {pass "vfork child follow, finish after tcatch vfork"}
322       -re "Run till exit from.*__kernel_v?syscall.*0x\[0-9a-fA-F\]* in vfork .*$gdb_prompt " {
323           send_gdb "finish\n"
324           exp_continue
325       }
326       -re "Run till exit from.*vfork.*${srcfile2}:9.*$gdb_prompt "\
327                       {pass "vfork child follow, finish after tcatch vfork (followed exec)"}
328       -re "$gdb_prompt $" {fail "vfork child follow, finish after tcatch vfork"}
329       timeout         {fail "(timeout) vfork child follow, finish after tcatch vfork" }
330    }
331    # The parent has been detached; allow time for any output it might
332    # generate to arrive, so that output doesn't get confused with
333    # any expected debugger output from a subsequent testpoint.
334    #
335    exec sleep 1
336 }
337
338 proc do_vfork_and_exec_tests {} {
339    global gdb_prompt
340
341    # Check that vfork catchpoints are supported, as an indicator for whether
342    # vfork-following is supported.
343    if [runto_main] then { check_vfork_catchpoints }
344
345    # Try following the parent process by stepping through a call to
346    # vfork.  Do this without catchpoints.
347    if [runto_main] then { vfork_parent_follow_through_step }
348
349    # Try following the parent process by setting a breakpoint on the
350    # other side of a vfork, and running to that point.  Do this
351    # without catchpoints.
352    if [runto_main] then { vfork_parent_follow_to_bp }
353
354    # Try following the child process by just continuing through the
355    # vfork, and letting the parent's breakpoint on "main" be auto-
356    # magically reset in the child.
357    #
358    if [runto_main] then { vfork_and_exec_child_follow_to_main_bp }
359
360    # Try following the child process by stepping through a call to
361    # vfork.  The child also executes an exec.  Since the child cannot
362    # be debugged until after it has exec'd, and since there's a bp on
363    # "main" in the parent, and since the bp's for the parent are
364    # recomputed in the exec'd child, the step through a vfork should
365    # land us in the "main" for the exec'd child, too.
366    #
367    if [runto_main] then { vfork_and_exec_child_follow_through_step }
368
369    # Try catching a vfork, and stepping out to the parent.
370    #
371    if [runto_main] then { tcatch_vfork_then_parent_follow }
372
373    # Try catching a vfork, and stepping out to the child.
374    #
375    if [runto_main] then { tcatch_vfork_then_child_follow }
376
377    # Test the ability to follow both child and parent of a vfork.  Do
378    # this without catchpoints.
379    # ??rehrauer: NYI.  Will add testpoints here when implemented.
380    #
381
382    # Test the ability to have the debugger ask the user at vfork-time
383    # whether to follow the parent, child or both.  Do this without
384    # catchpoints.
385    # ??rehrauer: NYI.  Will add testpoints here when implemented.
386    #
387 }
388
389 # Start with a fresh gdb
390
391 gdb_exit
392 gdb_start
393 gdb_reinitialize_dir $srcdir/$subdir
394 gdb_load ${binfile}
395
396 # The "Detaching..." and "Attaching..." messages may be hidden by
397 # default.
398 gdb_test_no_output "set verbose"
399
400 # This is a test of gdb's ability to follow the parent or child
401 # of a Unix vfork() system call.  (The child will subsequently
402 # call a variant of a Unix exec() system call.)
403 #
404 do_vfork_and_exec_tests
405
406 set timeout $oldtimeout
407 return 0