]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blob - gdb/testsuite/gdb.arch/arm-disp-step.exp
GDB copyright headers update after running GDB's copyright.py script.
[thirdparty/binutils-gdb.git] / gdb / testsuite / gdb.arch / arm-disp-step.exp
1 # Copyright 2010-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 # This file is part of the gdb testsuite.
17
18 # Test arm displaced stepping.
19
20 if {![is_aarch32_target]} then {
21 verbose "Skipping arm displaced stepping tests."
22 return
23 }
24
25 set testfile "arm-disp-step"
26 set srcfile ${testfile}.S
27 set binfile ${objdir}/${subdir}/${testfile}
28
29 set additional_flags "-Wa,-g"
30
31 if { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable [list debug $additional_flags]] != "" } {
32 untested arm-disp-step.exp
33 return -1
34 }
35
36
37 #########################################
38 # Test ldm/stm related to PC.
39 proc test_ldm_stm_pc {} {
40 global srcfile
41 global gdb_prompt
42
43 # Try to set breakpoint on test_ldm_stm_pc. If symbol 'test_ldm_stm_pc'
44 # can't be resolved, test case is compiled in Thumb mode, skip it.
45 gdb_test_multiple "break *test_ldm_stm_pc" "break test_ldm_stm_pc" {
46 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
47 pass "break test_ldm_stm_pc"
48 }
49 -re "No symbol.*\r\n$gdb_prompt $" {
50 pass "break test_ldm_stm_pc"
51 return 0
52 }
53 }
54
55 gdb_test "break *test_ldm_pc" \
56 "Breakpoint.*at.* file .*$srcfile, line.*" \
57 "break test_ldm_pc"
58 gdb_test "break *test_ldm_stm_pc_ret" \
59 "Breakpoint.*at.* file .*$srcfile, line.*" \
60 "break test_ldm_stm_pc_ret"
61
62 gdb_continue_to_breakpoint "continue to test_ldm_stm_pc" \
63 ".*stmdb.*sp\!\,.*\{lr\, pc\}.*"
64 gdb_continue_to_breakpoint "continue to test_ldm_pc" \
65 ".*ldmia.*sp\!\,.*\{pc\}.*"
66 gdb_continue_to_breakpoint "continue to test_ldm_stm_pc_ret" \
67 ".*bx lr.*"
68 }
69
70 #########################################
71 # Test ldrX literal
72 proc test_ldr_literal {} {
73 global srcfile
74 global gdb_prompt
75
76 gdb_test_multiple "break *test_ldr_literal" "break test_ldr_literal" {
77 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
78 pass "break test_ldr_literal"
79 }
80 -re "No symbol.*\r\n$gdb_prompt $" {
81 return 0
82 }
83 }
84
85 gdb_test "break *test_ldrsb_literal" \
86 "Breakpoint.*at.* file .*$srcfile, line.*" \
87 "break test_ldrsb_literal"
88 gdb_test "break *test_ldrsh_literal" \
89 "Breakpoint.*at.* file .*$srcfile, line.*" \
90 "break test_ldrsh_literal"
91 gdb_test "break *test_ldr_literal_end" \
92 "Breakpoint.*at.* file .*$srcfile, line.*" \
93 "break test_test_ldr_literal_end"
94
95 gdb_continue_to_breakpoint "continue to test_ldr_literal" \
96 ".*ldrh.*r0\,.*\[pc\].*"
97 gdb_continue_to_breakpoint "continue to test_ldrsb_literal" \
98 ".*ldrsb.*r0\,.*\[pc\].*"
99 gdb_continue_to_breakpoint "continue to test_ldrsh_literal" \
100 ".*ldrsh.*r0\,.*\[pc\].*"
101 gdb_continue_to_breakpoint "continue to test_ldr_literal_ret" \
102 ".*bx lr.*"
103 }
104
105 proc test_ldr_literal_16 {} {
106 global srcfile
107 global gdb_prompt
108
109 gdb_test_multiple "break *test_ldr_literal_16" "break test_ldr_literal_16" {
110 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
111 pass "break test_ldr_literal"
112 }
113 -re "No symbol.*\r\n$gdb_prompt $" {
114 return 0
115 }
116 }
117 gdb_test "break *test_ldr_literal_16_end" \
118 "Breakpoint.*at.* file .*$srcfile, line.*" \
119 "break test_ldr_literal_16_end"
120
121 gdb_continue_to_breakpoint "continue to test_ldr_literal_16" \
122 ".*ldr.*r0\,.*L2.*"
123 gdb_continue_to_breakpoint "continue to test_ldr_literal_16_end" \
124 ".*bx lr.*"
125 }
126
127 ##########################################
128 # Test call/ret.
129 proc test_call_ret {} {
130 global srcfile
131 global testfile
132
133 gdb_test "break *test_call" \
134 "Breakpoint.*at.* file .*$srcfile, line.*" \
135 "break test_call"
136
137 gdb_test "break *test_call_end" \
138 "Breakpoint.*at.* file .*$srcfile, line.*" \
139 "break test_call_end"
140 gdb_test "break *test_ret" \
141 "Breakpoint.*at.* file .*$srcfile, line.*" \
142 "break test_ret"
143 gdb_test "break *test_ret_end" \
144 "Breakpoint.*at.* file .*$srcfile, line.*" \
145 "break test_ret_end"
146
147 gdb_continue_to_breakpoint "test_call" ".*bl test_call_subr.*"
148 gdb_continue_to_breakpoint "test_call_end" \
149 ".*@ Location test_call_end.*"
150 gdb_continue_to_breakpoint "test_ret" \
151 ".*bx lr.*"
152 gdb_continue_to_breakpoint "continue to test_ret_end" \
153 ".*@ Location test_ret_end.*"
154 }
155
156
157 #########################################
158 # Test branch
159 proc test_branch {} {
160 global srcfile
161 gdb_test "break *test_branch" \
162 "Breakpoint.*at.* file .*$srcfile, line.*" \
163 "break test_branch"
164 gdb_test "break *L_branch" \
165 "Breakpoint.*at.* file .*$srcfile, line.*" \
166 "break Lbranch"
167
168 gdb_continue_to_breakpoint "continue to test_branch" \
169 ".*b.*L_branch.*"
170 gdb_continue_to_breakpoint "continue to Lbranch" \
171 ".*bx lr.*"
172 }
173
174 #########################################
175
176 # Test ldr from pc
177 proc test_ldr_from_pc {} {
178 global srcfile
179 gdb_test "break *test_ldr_pc" \
180 "Breakpoint.*at.* file .*$srcfile, line.*" \
181 "break test_ldr_pc"
182 gdb_test "break test_ldr_pc_ret" \
183 "Breakpoint.*at.* file .*$srcfile, line.*" \
184 "break test_ldr_pc_ret"
185
186 gdb_continue_to_breakpoint "continue to test_ldr_pc" \
187 ".*ldr.*r1\,.*\[pc, #0\].*"
188 gdb_continue_to_breakpoint "continue to test_ldr_pc_ret" \
189 ".*bx lr.*"
190 }
191
192 #########################################
193
194 # Test cbz and cbnz
195 proc test_cbz_cbnz {} {
196 global srcfile
197 global gdb_prompt
198
199 gdb_test_multiple "break *test_zero_cbnz" "break test_zero_cbnz" {
200 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
201 pass "break test_ldr_literal"
202 }
203 -re "No symbol.*\r\n$gdb_prompt $" {
204 return 0
205 }
206 }
207
208 gdb_test "break *test_zero_cbz" \
209 "Breakpoint.*at.* file .*$srcfile, line.*" \
210 "break test_zero_cbz"
211 gdb_test "break *test_non_zero_cbnz" \
212 "Breakpoint.*at.* file .*$srcfile, line.*" \
213 "break test_non_zero_cbnz"
214 gdb_test "break *test_non_zero_cbz" \
215 "Breakpoint.*at.* file .*$srcfile, line.*" \
216 "break test_non_zero_cbz"
217
218 gdb_continue_to_breakpoint "continue to test_zero_cbnz" \
219 ".*cbnz.*r0\,.*\.L3.*"
220 gdb_continue_to_breakpoint "continue to test_zero_cbz" \
221 ".*cbz.*r0\,.*\.L3.*"
222 gdb_continue_to_breakpoint "continue to test_non_zero_cbz" \
223 ".*cbz.*r0\,.*\.L4.*"
224 gdb_continue_to_breakpoint "continue to test_non_zero_cbnz" \
225 ".*cbnz.*r0\,.*\.L4.*"
226 }
227
228 # Test adr
229
230 proc test_adr {} {
231 global srcfile
232 global gdb_prompt
233
234 gdb_test_multiple "break *test_adr" "break test_adr" {
235 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
236 pass "break test_adr"
237 }
238 -re "No symbol.*\r\n$gdb_prompt $" {
239 return 0
240 }
241 }
242
243 gdb_test "break *test_adr_end" \
244 "Breakpoint.*at.* file .*$srcfile, line.*" \
245 "break test_adr_end"
246
247 gdb_continue_to_breakpoint "test_adr" \
248 ".*adr.*r0\,.*\.L8.*"
249 gdb_continue_to_breakpoint "test_adr_end" \
250 ".*bx lr.*"
251 }
252
253 proc test_adr_32bit {} {
254 global srcfile
255 global gdb_prompt
256
257 gdb_test_multiple "break *test_adr_32bit" "break test_adr_32bit" {
258 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
259 pass "break test_adr"
260 }
261 -re "No symbol.*\r\n$gdb_prompt $" {
262 return 0
263 }
264 }
265
266 gdb_test "break *test_adr_32bit_after" \
267 "Breakpoint.*at.* file .*$srcfile, line.*" \
268 "break test_adr_32bit_after"
269
270 gdb_test "break *test_adr_32bit_end" \
271 "Breakpoint.*at.* file .*$srcfile, line.*" \
272 "break test_adr_32bit_end"
273
274 gdb_continue_to_breakpoint "test_adr_32bit" \
275 ".*adr.*r0\,.*\.L6.*"
276 gdb_continue_to_breakpoint "test_adr_32bit_after" \
277 ".*adr.*r0\,.*\.L6.*"
278 gdb_continue_to_breakpoint "test_adr_32bit_end" \
279 ".*bx lr.*"
280 }
281
282 #########################################
283 # Test pop to PC
284 proc test_pop_pc {} {
285 global srcfile
286 gdb_test "break *test_pop_pc_1" \
287 "Breakpoint.*at.* file .*$srcfile, line.*" \
288 "break test_pop_pc_1"
289 gdb_test "break *test_pop_pc_2" \
290 "Breakpoint.*at.* file .*$srcfile, line.*" \
291 "break test_pop_pc_2"
292 gdb_test "break *test_pop_pc_3" \
293 "Breakpoint.*at.* file .*$srcfile, line.*" \
294 "break test_pop_pc_3"
295
296 gdb_test "break *test_pop_pc_ret" \
297 "Breakpoint.*at.* file .*$srcfile, line.*" \
298 "break test_pop_pc_ret"
299
300 gdb_test "break *test_pop_pc_1_right" \
301 "Breakpoint.*at.* file .*$srcfile, line.*" \
302 "break test_pop_pc_1_right"
303 gdb_test "break *test_pop_pc_1_wrong" \
304 "Breakpoint.*at.* file .*$srcfile, line.*" \
305 "break test_pop_pc_1_wrong"
306 gdb_test "break *test_pop_pc_2_right" \
307 "Breakpoint.*at.* file .*$srcfile, line.*" \
308 "break test_pop_pc_2_right"
309 gdb_test "break *test_pop_pc_2_wrong" \
310 "Breakpoint.*at.* file .*$srcfile, line.*" \
311 "break test_pop_pc_2_wrong"
312 gdb_test "break *test_pop_pc_3_right" \
313 "Breakpoint.*at.* file .*$srcfile, line.*" \
314 "break test_pop_pc_3_right"
315 gdb_test "break *test_pop_pc_3_wrong" \
316 "Breakpoint.*at.* file .*$srcfile, line.*" \
317 "break test_pop_pc_1_wrong"
318
319 gdb_continue_to_breakpoint "continue to test_pop_pc_1" \
320 ".*b.*\{r1\, pc\}.*"
321 gdb_continue_to_breakpoint "continue to test_pop_pc_1_check" \
322 ".*b.*right.*"
323
324 gdb_continue_to_breakpoint "continue to test_pop_pc_2" \
325 ".*\{pc\}.*"
326 gdb_continue_to_breakpoint "continue to test_pop_pc_2_check" \
327 ".*b.*right.*"
328 gdb_continue_to_breakpoint "continue to test_pop_pc_3" \
329 ".*\{r0\,r1\,r2\,r3\,r4\,r5\,r6\,r7\,pc\}.*"
330 gdb_continue_to_breakpoint "continue to test_pop_pc_3_check" \
331 ".*b.*right.*"
332 gdb_continue_to_breakpoint "continue to test_pop_pc_ret" \
333 ".*r7.*"
334 }
335
336 ###########################################
337
338 proc test_str_pc {} {
339 global srcfile
340 global gdb_prompt
341
342 gdb_test_multiple "break *test_str_pc" "break test_str_pc" {
343 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
344 pass "break test_str_pc"
345 }
346 -re "No symbol.*\r\n$gdb_prompt $" {
347 pass "break test_str_pc"
348 return
349 }
350 }
351 gdb_test "break *test_str_pc_end" \
352 "Breakpoint.*at.* file .*$srcfile, line.*" \
353 "break test_str_pc_end"
354
355 # Set breakpoint on both lables pc_offset_right and pc_offset_wrong
356 gdb_test "break *pc_offset_right" \
357 "Breakpoint.*at.* file .*$srcfile, line.*" \
358 "break pc_offset_right"
359 gdb_test "break *pc_offset_wrong" \
360 "Breakpoint.*at.* file .*$srcfile, line.*" \
361 "break pc_offset_wrong"
362
363 gdb_continue_to_breakpoint "continue to test_str_pc" \
364 ".*str.*pc\,.*\[sp, #-4\].*"
365 # If breakpoint on lable pc_offset_wrong is hit, that means the offset
366 # computed in displaced stepping is different from offset computed
367 # without displaced stepping. Report a failure.
368 gdb_continue_to_breakpoint "continue to pc_offset_right" \
369 ".*b.*test_str_pc_end.*"
370 gdb_continue_to_breakpoint "continue to test_str_pc_end" \
371 ".*bx lr.*"
372 }
373
374 # Test 16 bit thumb instruction 'add rd, pc'.
375
376 proc test_add_rn_pc {} {
377 global srcfile gdb_prompt
378
379 set test "break test_add_rn_pc"
380 gdb_test_multiple "break *test_add_rn_pc" $test {
381 -re "Breakpoint.*at.* file .*$srcfile, line.*\r\n$gdb_prompt $" {
382 pass $test
383 }
384 -re "No symbol.*\r\n$gdb_prompt $" {
385 return
386 }
387 }
388
389 gdb_continue_to_breakpoint "continue to test_add_rn_pc" \
390 ".*mov.*r3, 4.*"
391
392 gdb_test "break *test_add_rn_pc_start" \
393 "Breakpoint.*at.* file .*$srcfile, line.*" \
394 "break test_add_rn_pc_start"
395
396 gdb_continue_to_breakpoint "continue to test_add_rn_pc_start" \
397 ".*add.*r3,.*pc.*"
398
399 set pc_val [get_integer_valueof "\$pc" 0]
400
401 gdb_test "break *test_add_rn_pc_end" \
402 "Breakpoint.*at.* file .*$srcfile, line.*" \
403 "break test_add_rn_pc_end"
404
405 gdb_continue_to_breakpoint "continue to test_add_rn_pc_end" \
406 ".*bx lr.*"
407
408 set r3_val [get_integer_valueof "\$r3" 0]
409 # Test the value in r3 is correct.
410 gdb_assert { [expr {$pc_val + 4 + 4} == $r3_val] }
411 }
412
413 # Get things started.
414
415 clean_restart ${testfile}
416
417 # Turn displaced stepping off before runto main. When displaced stepping
418 # is on, and we type 'run', GDB will first try to single step on _dl_debug_state,
419 # which is in library might be compiled in Thumb.
420 gdb_test_no_output "set displaced-stepping off"
421
422 if ![runto_main] then {
423 fail "Can't run to main"
424 return 0
425 }
426
427 gdb_test_no_output "set displaced-stepping on"
428 gdb_test "show displaced-stepping" ".* displaced stepping .* is on.*"
429
430 test_call_ret
431
432 test_branch
433
434 test_ldr_from_pc
435
436 test_ldm_stm_pc
437
438 test_ldr_literal
439
440 test_ldr_literal_16
441
442 test_cbz_cbnz
443
444 test_adr
445
446 test_adr_32bit
447
448 test_pop_pc
449
450 test_str_pc
451
452 test_add_rn_pc
453
454 ##########################################
455
456 # Done, run program to exit.
457
458 gdb_continue_to_end "arm-disp-step"