Commit | Line | Data |
---|---|---|
19fa4a0a MW |
1 | # Copyright (C) 1992 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 2 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, write to the Free Software | |
15 | # Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ | |
16 | ||
17 | # Please email any bugs, comments, and/or additions to this file to: | |
c79f61db | 18 | # bug-gdb@prep.ai.mit.edu |
19fa4a0a MW |
19 | |
20 | # This file was written by Fred Fish. (fnf@cygnus.com) | |
21 | ||
22 | # Generic gdb subroutines that should work for any target. If these | |
23 | # need to be modified for any target, it can be done with a variable | |
24 | # or by passing arguments. | |
25 | ||
26 | # | |
27 | # gdb_unload -- unload a file if one is loaded | |
28 | # | |
29 | ||
30 | proc gdb_unload {} { | |
31 | global verbose | |
32 | global GDB | |
33 | global prompt | |
34 | send "file\n" | |
35 | expect { | |
36 | -re "No exec file now\.\r" { continue -expect } | |
37 | -re "No symbol file now\.\r" { continue -expect } | |
38 | -re "A program is being debugged already..*Kill it\? \(y or n\) $"\ | |
39 | { send "y\n" | |
40 | if $verbose>1 then { | |
41 | send_user "\t\tKilling previous program being debugged\n" | |
42 | } | |
43 | continue -expect | |
44 | } | |
45 | -re "Discard symbol table from .*\? \(y or n\) $" { | |
46 | send "y\n" | |
47 | continue -expect | |
48 | } | |
49 | -re "$prompt $" {} | |
50 | timeout { | |
51 | error "couldn't unload file in $GDB (timed out)." | |
c79f61db | 52 | return -1 |
19fa4a0a MW |
53 | } |
54 | } | |
55 | } | |
56 | ||
57 | # Many of the tests depend on setting breakpoints at various places and | |
58 | # running until that breakpoint is reached. At times, we want to start | |
59 | # with a clean-slate with respect to breakpoints, so this utility proc | |
60 | # lets us do this without duplicating this code everywhere. | |
61 | # | |
62 | ||
63 | proc delete_breakpoints {} { | |
64 | global prompt | |
65 | ||
66 | send "delete breakpoints\n" | |
67 | expect { | |
68 | -re "Delete all breakpoints\? \(y or n\) $" { | |
69 | send "y\n" | |
70 | continue -expect | |
71 | } | |
72 | -re "y\r\n$prompt $" {} | |
73 | -re ".*$prompt $" { fail "Delete all breakpoints" ; return } | |
74 | timeout { fail "Delete all breakpoints (timeout)" ; return } | |
75 | } | |
76 | send "info breakpoints\n" | |
77 | expect { | |
78 | -re "No breakpoints or watchpoints..*$prompt $" {} | |
79 | -re ".*$prompt $" { fail "breakpoints not deleted" ; return } | |
80 | timeout { fail "info breakpoints (timeout)" ; return } | |
81 | } | |
82 | } | |
83 | ||
84 | ||
85 | # | |
86 | # Set breakpoint at function and run gdb until it breaks there. | |
87 | # Since this is the only breakpoint that will be set, if it stops | |
88 | # at a breakpoint, we will assume it is the one we want. We can't | |
89 | # just compare to "function" because it might be a fully qualified, | |
90 | # single quoted C++ function specifier. | |
91 | # | |
92 | ||
93 | proc runto { function } { | |
94 | global prompt | |
95 | global decimal | |
96 | ||
97 | send "delete\n" | |
98 | expect { | |
99 | -re "Delete all breakpoints\? \(y or n\) $" { | |
100 | send "y\n" | |
101 | expect { | |
102 | -re "$prompt $" {} | |
103 | timeout { fail "deleting breakpoints (timeout)" ; return 0 } | |
104 | } | |
105 | } | |
106 | -re ".*$prompt $" {} | |
107 | timeout { fail "deleting breakpoints (timeout)" ; return 0 } | |
108 | } | |
109 | ||
110 | send "break $function\n" | |
c79f61db | 111 | # The first regexp is what we get with -g, the second without -g. |
19fa4a0a MW |
112 | expect { |
113 | -re "Break.* at .*: file .*, line $decimal.\r\n$prompt $" {} | |
c79f61db | 114 | -re "Breakpoint \[0-9\]* at 0x\[0-9a-f\]*.*$prompt $" {} |
19fa4a0a MW |
115 | -re "$prompt $" { fail "setting breakpoint at $function" ; return 0 } |
116 | timeout { fail "setting breakpoint at $function (timeout)" ; return 0 } | |
117 | } | |
118 | ||
119 | send "run\n" | |
c79f61db RS |
120 | # the "at foo.c:36" output we get with -g. |
121 | # the "in func" output we get without -g. | |
19fa4a0a MW |
122 | expect { |
123 | -re "The program .* has been started already.* \(y or n\) $" { | |
124 | send "y\n" | |
125 | continue -expect | |
126 | } | |
c79f61db RS |
127 | -re "Starting.*Break.* at .*:$decimal.*$prompt $" { return 1 } |
128 | -re "Breakpoint \[0-9\]*, \[0-9xa-f\]* in $function.*$prompt $" { | |
129 | return 1 | |
130 | } | |
19fa4a0a MW |
131 | -re "$prompt $" { fail "running to $function" ; return 0 } |
132 | timeout { fail "running to $function (timeout)" ; return 0 } | |
133 | } | |
134 | } | |
135 | ||
136 | # | |
137 | # gdb_test -- send a command to gdb and test the result. | |
138 | # Takes three parameters. | |
139 | # Parameters: | |
140 | # First one is the command to execute, | |
141 | # Second one is the pattern to match for a PASS, | |
142 | # Third one is an optional message to be printed. If this | |
143 | # a null string "", then the pass/fail messages are not printed. | |
144 | # Returns: | |
145 | # 1 if the test failed, | |
146 | # 0 if the test passes, | |
147 | # -1 if there was an internal error. | |
148 | # | |
149 | proc gdb_test { args } { | |
150 | global verbose | |
151 | global prompt | |
152 | global GDB | |
153 | global spawn_id | |
154 | ||
155 | if [llength $args]==3 then { | |
156 | set message [lindex $args 2] | |
157 | } else { | |
158 | set message [lindex $args 0] | |
159 | } | |
160 | set command [lindex $args 0] | |
161 | set pattern [lindex $args 1] | |
162 | ||
163 | if $verbose>2 then { | |
164 | send_user "Sending \"$command\" to gdb\n" | |
165 | send_user "Looking to match \"$pattern\"\n" | |
166 | send_user "Message is \"$message\"\n" | |
167 | } | |
168 | ||
169 | set result -1 | |
170 | set errmess "" | |
171 | # trap the send so any problems don't crash things | |
172 | catch "send \"$command\n\"" errmess | |
c79f61db RS |
173 | if [string match "write\(spawn_id=\[0-9\]+\):" $errmess] then { |
174 | error "sent \"$command\" got expect error \"$errmess\"" | |
175 | catch "close" | |
176 | gdb_start | |
19fa4a0a MW |
177 | return -1 |
178 | } | |
179 | ||
180 | expect { | |
181 | -re ".*Ending remote debugging.*$prompt$" { | |
182 | if ![isnative] then { | |
183 | warning "Can`t communicate to remote target." | |
184 | } | |
185 | gdb_exit | |
186 | gdb_start | |
187 | set result -1 | |
188 | } | |
189 | -re "$pattern.*$prompt $" { | |
190 | if ![string match "" $message] then { | |
191 | pass "$message" | |
192 | } | |
193 | set result 0 | |
194 | } | |
195 | -re "Undefined command:.*$prompt" { | |
196 | error "Undefined command \"$command\"." | |
c79f61db | 197 | set result 1 |
19fa4a0a MW |
198 | } |
199 | -re "Ambiguous command.*$prompt $" { | |
200 | error "\"$command\" is not a unique command name." | |
c79f61db | 201 | set result 1 |
19fa4a0a MW |
202 | } |
203 | -re ".*$prompt $" { | |
204 | if ![string match "" $message] then { | |
205 | fail "$message" | |
206 | } | |
207 | set result 1 | |
208 | } | |
209 | "<return>" { | |
210 | send "\n" | |
211 | error "Window too small." | |
212 | } | |
213 | -re "\(y or n\) " { | |
214 | send "n\n" | |
215 | error "Got interactive prompt." | |
216 | } | |
c79f61db RS |
217 | eof { |
218 | error "Process no longer exists" | |
219 | return -1 | |
220 | } | |
19fa4a0a MW |
221 | buffer_full { |
222 | error "internal buffer is full." | |
223 | } | |
19fa4a0a MW |
224 | timeout { |
225 | fail "(timeout) $message" | |
226 | set result 1 | |
227 | } | |
228 | } | |
229 | return $result | |
230 | } | |
231 | ||
19fa4a0a MW |
232 | proc gdb_reinitialize_dir { subdir } { |
233 | global prompt | |
234 | global verbose | |
235 | ||
236 | send "dir\n" | |
237 | expect { | |
238 | -re "Reinitialize source path to empty.*" { | |
239 | send "y\n" | |
240 | expect { | |
241 | -re "Source directories searched.*$prompt $" { | |
242 | send "dir $subdir\n" | |
243 | expect { | |
244 | -re "Source directories searched.*$prompt $" { | |
245 | if $verbose>1 then { | |
246 | send_user "Dir set to $subdir\n" | |
247 | } | |
248 | } | |
249 | -re ".*$prompt $" { | |
250 | error "Dir \"$subdir\" failed." | |
251 | } | |
252 | } | |
253 | } | |
254 | -re ".*$prompt $" { | |
255 | error "Dir \"$subdir\" failed." | |
256 | } | |
257 | } | |
258 | } | |
259 | -re ".*$prompt $" { | |
260 | error "Dir \"$subdir\" failed." | |
261 | } | |
262 | } | |
263 | } | |
c79f61db RS |
264 | |
265 | ||
266 | # | |
267 | # gdb_exit -- exit the GDB, killing the target program if necessary | |
268 | # | |
269 | proc default_gdb_exit {} { | |
270 | global GDB | |
271 | global GDBFLAGS | |
272 | global verbose | |
273 | ||
274 | verbose "Quitting $GDB $GDBFLAGS" 1 | |
275 | ||
276 | # This used to be 1 for unix-gdb.exp | |
277 | set timeout 5 | |
278 | ||
279 | catch "send \"quit\n\"" result | |
280 | # If the process has gone away (e.g. gdb dumped core), deal with it. | |
281 | if [string match "write\(spawn_id=\[0-9\]+\):" $result] then { | |
282 | catch "close" | |
283 | # FIXME: Shouldn't we call "wait" too? | |
284 | return -1 | |
285 | } | |
286 | # FIXME: What is this catch statement doing here? Won't it prevent us | |
287 | # from getting errors that we'd rather see? | |
288 | catch { | |
289 | expect { | |
290 | eof { | |
291 | verbose "Got EOF from $GDB" 2 | |
292 | } | |
293 | timeout { | |
294 | verbose "Got TIMEOUT from $GDB" 2 | |
295 | } | |
296 | -re "The program is running. Quit anyway.*(y or n) $" { | |
297 | send "y\n" | |
298 | verbose "Killing program being debugged" 2 | |
299 | } | |
300 | } | |
301 | } | |
302 | ||
303 | # FIXME: Does the catch prevent us from getting errors that we'd rather | |
304 | # see? the old gdb_exit in unix-gdb.exp had "close" without catch | |
305 | # in the above expect statement (for the timeout and -re "The | |
306 | # program... cases) (as well as a catch "close" here). | |
307 | catch "close" | |
308 | ||
309 | # Before this was here sometimes "uit" would get sent to the next GDB | |
310 | # (assuming this is immediately followed by gdb_start), which would | |
311 | # cause a loss of syncronization (i.e. all the stuff that swallows a | |
312 | # prompt would swallow the wrong one). | |
313 | wait | |
314 | } | |
315 | ||
316 | ||
317 | ||
318 |