summaryrefslogtreecommitdiff
path: root/gdb/testsuite/gdb.mi/mi-break.exp
blob: 4c99a24f79fc4f6aa09edef66aae2452bdd2f3ad (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
# Copyright 1999-2013 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 essential Machine interface (MI) operations
#
# Verify that, using the MI, we can run a simple program and perform basic
# debugging activities like: insert breakpoints, run the program,
# step, next, continue until it ends and, last but not least, quit.
#
# The goal is not to test gdb functionality, which is done by other tests,
# but to verify the correct output response to MI operations.
#

load_lib mi-support.exp
set MIFLAGS "-i=mi"

gdb_exit
if [mi_gdb_start] {
    continue
}

standard_testfile basics.c

if  { [gdb_compile "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug}] != "" } {
     untested mi-break.exp
     return -1
}

mi_delete_breakpoints
mi_gdb_reinitialize_dir $srcdir/$subdir
mi_gdb_load ${binfile}

# Locate line numbers in basics.c.
set line_callee4_head  [gdb_get_line_number "callee4 ("]
set line_callee4_body  [expr $line_callee4_head + 2]
set line_callee3_head  [gdb_get_line_number "callee3 ("]
set line_callee3_body  [expr $line_callee3_head + 2]
set line_callee2_head  [gdb_get_line_number "callee2 ("]
set line_callee2_body  [expr $line_callee2_head + 2]
set line_callee1_head  [gdb_get_line_number "callee1 ("]
set line_callee1_body  [expr $line_callee1_head + 2]
set line_main_head     [gdb_get_line_number "main ("]
set line_main_body     [expr $line_main_head + 2]
set line_callme_head   [gdb_get_line_number "callme ("]
set line_callme_body   [expr $line_callme_head + 2]

set fullname "fullname=\"${fullname_syntax}${srcfile}\""

proc test_tbreak_creation_and_listing {} {
    global mi_gdb_prompt
    global srcfile
    global hex
    global line_callee4_head line_callee4_body
    global line_callee3_head line_callee3_body
    global line_callee2_head line_callee2_body
    global line_callee1_head line_callee1_body
    global line_main_head    line_main_body
    global fullname

    # Insert some breakpoints and list them
    # Also, disable some so they do not interfere with other tests
    # Tests:
    # -break-insert -t main
    # -break-insert -t basics.c:callee2
    # -break-insert -t basics.c:$line_callee3_head
    # -break-insert -t srcfile:$line_callee4_head
    # -break-list

    mi_create_breakpoint "-t main" 1 del main ".*basics.c" $line_main_body $hex \
             "break-insert -t operation"

    mi_create_breakpoint "-t basics.c:callee2" 2 del callee2 ".*basics.c" $line_callee2_body $hex \
             "insert temp breakpoint at basics.c:callee2"

    mi_create_breakpoint "-t basics.c:$line_callee3_head" 3 del callee3 ".*basics.c" $line_callee3_head $hex \
             "insert temp breakpoint at basics.c:\$line_callee3_head"

    # Getting the quoting right is tricky.  That is "\"<file>\":$line_callee4_head"
    mi_create_breakpoint "-t \"\\\"${srcfile}\\\":$line_callee4_head\"" 4 del callee4 ".*basics.c" $line_callee4_head $hex \
             "insert temp breakpoint at \"<fullfilename>\":\$line_callee4_head"

    mi_gdb_test "666-break-list" \
     	    "666\\\^done,BreakpointTable=\{nr_rows=\".\",nr_cols=\".\",hdr=\\\[\{width=\".*\",alignment=\".*\",col_name=\"number\",colhdr=\"Num\"\}.*colhdr=\"Type\".*colhdr=\"Disp\".*colhdr=\"Enb\".*colhdr=\"Address\".*colhdr=\"What\".*\\\],body=\\\[bkpt=\{number=\"1\",type=\"breakpoint\",disp=\"del\",enabled=\"y\",addr=\"$hex\",func=\"main\",file=\".*basics.c\",${fullname},line=\"$line_main_body\",times=\"0\",original-location=\".*\"\}.*\\\]\}" \
                "list of breakpoints"

    mi_gdb_test "777-break-delete" \
	    "777\\^done" \
	    "delete temp breakpoints"
}

proc test_rbreak_creation_and_listing {} {
    global mi_gdb_prompt
    global srcfile
    global hex
    global line_callee4_head line_callee4_body
    global line_callee3_head line_callee3_body
    global line_callee2_head line_callee2_body
    global line_callee1_head line_callee1_body
    global line_main_head    line_main_body

    # Insert some breakpoints and list them
    # Also, disable some so they do not interfere with other tests
    # Tests:
    # -break-insert -r main
    # -break-insert -r callee2
    # -break-insert -r callee
    # -break-insert -r .*llee
    # -break-list

    setup_kfail "*-*-*" mi/14270
    mi_gdb_test "122-break-insert -r main" \
             "122\\^done,bkpt=\{number=\"5\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_main_body\"\}" \
             "break-insert -r operation"

    setup_kfail "*-*-*" mi/14270
    mi_gdb_test "133-break-insert -r callee2" \
             "133\\^done,bkpt=\{number=\"6\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee2_body\"\}" \
             "insert breakpoint with regexp callee2"

    setup_kfail "*-*-*" mi/14270
    mi_gdb_test "144-break-insert -r callee" \
	    "144\\^done,bkpt=\{number=\"7\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee1_body\"\},bkpt=\{number=\"8\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee2_body\"\},bkpt=\{number=\"9\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee3_body\"\},bkpt=\{number=\"10\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee4_body\"\}" \
             "insert breakpoint with regexp callee"

    setup_kfail "*-*-*" mi/14270
    mi_gdb_test "155-break-insert -r \.\*llee" \
	    "155\\^done,bkpt=\{number=\"11\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee1_body\"\},bkpt=\{number=\"12\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee2_body\"\},bkpt=\{number=\"13\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee3_body\"\},bkpt=\{number=\"14\",addr=\"$hex\",file=\".*basics.c\",line=\"$line_callee4_body\"\}" \
             "insert breakpoint with regexp .*llee"

    setup_kfail "*-*-*" mi/14270
    mi_gdb_test "166-break-list" \
	    "1\\\^done,BreakpointTable=\{nr_rows=\".\",nr_cols=\".\",hdr=\\\[\{width=\".*\",alignment=\".*\",col_name=\"number\",colhdr=\"Num\"\}.*colhdr=\"Type\".*colhdr=\"Disp\".*colhdr=\"Enb\".*colhdr=\"Address\".*colhdr=\"What\".*\\\],body=\\\[bkpt=\{number=\"5\",type=\"breakpoint\",disp=\"keep\",enabled=\"y\",addr=\"$hex\",func=\"main\",file=\".*basics.c\",line=\"$line_main_body\",times=\"0\"\},.*\}\\\]\}" \
                "list of breakpoints"

    mi_gdb_test "177-break-delete" \
	    "177\\^done" \
	    "delete temp breakpoints"
}

proc test_abreak_creation {} {
    mi_create_varobj tpnum \$tpnum "create local variable tpnum"
    # Test that $tpnum is not set before creating a tracepoint.
    mi_gdb_test "521-var-evaluate-expression tpnum" \
	"521\\^done,value=\"void\"" "eval tpnum before tracepoint"

    mi_gdb_test "522-break-insert -a main" \
	"522\\^done,bkpt=\{number=\"10\",type=\"tracepoint\".*\"\}" \
	"break-insert -a operation"

    mi_gdb_test "523-var-update tpnum" \
	"523\\^done,changelist=\\\[\{name=\"tpnum\",in_scope=\"true\",type_changed=\"false\",has_more=\"0\"\}\\\]" \
	"update tpnum"
    # Test that $tpnum is updated after creating a tracepoint.
    mi_gdb_test "524-var-evaluate-expression tpnum" \
	"524\\^done,value=\"10\"" "eval tpnum after tracepoint"
}

proc test_ignore_count {} {
    global mi_gdb_prompt
    global line_callme_body

    mi_gdb_test "-break-insert -i 1 callme" \
        "\\^done.*ignore=\"1\".*" \
        "insert breakpoint with ignore count at callme"

    mi_run_cmd

    mi_expect_stop "breakpoint-hit" "callme" "\{name=\"i\",value=\"2\"\}" ".*basics.c" $line_callme_body \
        {"" "disp=\"keep\"" } "run to breakpoint with ignore count"
}

proc test_error {} {
    global mi_gdb_prompt

    mi_gdb_test "-break-insert function_that_does_not_exist" \
        ".*\\^error,msg=\"Function \\\\\"function_that_does_not_exist\\\\\" not defined.\"" \
        "breakpoint at nonexistent function"

    # We used to have a bug whereby -break-insert that failed would not
    # clear some event hooks.  As result, whenever we evaluate expression
    # containing function call, the internal breakpoint created to handle
    # function call would be reported, messing up MI output.
    mi_gdb_test "-var-create V * return_1()" \
        "\\^done,name=\"V\",numchild=\"0\",value=\"1\",type=\"int\",has_more=\"0\"" \
        "create varobj for function call"

    mi_gdb_test "-var-update *" \
        "\\^done,changelist=\\\[\\\]" \
        "update varobj for function call"    
}

proc test_disabled_creation {} {
    global mi_gdb_prompt
    global hex
    global line_callee2_body

    mi_gdb_test "-break-insert -d basics.c:callee2" \
        "\\^done,bkpt=\{number=\"6\",type=\"breakpoint\",disp=\"keep\",enabled=\"n\",addr=\"$hex\",func=\"callee2\",file=\".*basics.c\",fullname=\".*\",line=\"$line_callee2_body\",times=\"0\",original-location=\".*\"\}" \
        "test disabled creation"

    mi_gdb_test "-break-delete" \
	    "\\^done" \
            "test disabled creation: cleanup"
}

proc test_breakpoint_commands {} {
    global line_callee2_body
    global hex
    global fullname

    mi_create_breakpoint "basics.c:callee2" 7 keep callee2 ".*basics.c" $line_callee2_body $hex \
             "breakpoint commands: insert breakpoint at basics.c:callee2"

    mi_gdb_test "-break-commands 7 \"print 10\" \"continue\"" \
        "\\^done" \
        "breakpoint commands: set commands"

    mi_gdb_test "-break-info 7" \
    	"\\^done,BreakpointTable=\{nr_rows=\".\",nr_cols=\".\",hdr=\\\[\{width=\".*\",alignment=\".*\",col_name=\"number\",colhdr=\"Num\"\}.*colhdr=\"Type\".*colhdr=\"Disp\".*colhdr=\"Enb\".*colhdr=\"Address\".*colhdr=\"What\".*\\\],body=\\\[bkpt=\{number=\"7\",type=\"breakpoint\",disp=\"keep\",enabled=\"y\",addr=\"$hex\",func=\"callee2\",file=\".*basics.c\",${fullname},line=\"$line_callee2_body\",times=\"0\",script=\{\"print 10\",\"continue\"\},original-location=\".*\"\}.*\\\]\}" \
        "breakpoint commands: check that commands are set"

    mi_gdb_test "-break-commands 7" \
        "\\^done" \
        "breakpoint commands: clear commands"

    mi_list_breakpoints [list [list 7 "keep" "callee2" "basics.c" "$line_callee2_body" $hex]] \
        "breakpoint commands: check that commands are cleared"

    mi_run_to_main

    mi_create_breakpoint "basics.c:callee2" 9 keep callee2 ".*basics.c" $line_callee2_body $hex \
             "breakpoint commands: insert breakpoint at basics.c:callee2, again"

    mi_gdb_test "-break-commands 9 \"set \$i=0\" \"while \$i<10\" \"print \$i\" \"set \$i=\$i+1\" \"end\" \"continue\" " \
        "\\^done" \
        "breakpoint commands: set commands"

    mi_send_resuming_command "exec-continue" "breakpoint commands: continue"

    set test "intermediate stop and continue"
    gdb_expect {
        -re ".*\\\$1 = 0.*\\\$10 = 9.*\\*running" {
	    pass $test
	}
        timeout {
	    fail $test
        }
    }

    mi_expect_stop "exited-normally" "" "" "" "" "" "test hitting breakpoint with commands"
}

test_tbreak_creation_and_listing
test_rbreak_creation_and_listing

test_ignore_count

test_error

test_disabled_creation

test_breakpoint_commands

test_abreak_creation

mi_gdb_exit
return 0