Skip to content

Commit a880623

Browse files
author
Yao Qi
committed
Initialize target description early in IPA
Target descriptions are allocated lazily, that is fine in GDBserver, but it is not safe to call malloc in gdb_collect in IPA, because we can set a fast tracepoint in malloc, and when the tracepoint is hit, gdb_collect/malloc is called, deadlock or memory corruption may be triggered. #0 0xf7cfc200 in malloc () #1 0xf7efdc07 in operator new(unsigned int) () #2 0xf7ef7636 in allocate_target_description() () #3 0xf7efcbe1 in i386_create_target_description(unsigned long long, bool) () #4 0xf7efb474 in i386_linux_read_description(unsigned long long) () #5 0xf7efb190 in get_ipa_tdesc(int) () #6 0xf7ef9baa in gdb_collect () The fix is to initialize all target descriptions earlier, when the IPA is loaded. In order to guarantee malloc is not called in IPA in gdb_collect, I change the test to set a breakpoint on malloc, if IPA gdb_collect calls malloc, program will hit the breakpoint, and test fail. continue Continuing. Thread 1 "" hit Breakpoint 5, 0xf7cfc200 in malloc () (gdb) FAIL: gdb.trace/ftrace.exp: advance through tracing gdb/gdbserver: 2017-12-07 Yao Qi <yao.qi@linaro.org> * linux-aarch64-ipa.c (initialize_low_tracepoint): Call aarch64_linux_read_description. * linux-amd64-ipa.c (idx2mask): New array. (get_ipa_tdesc): Move idx2mask out. (initialize_low_tracepoint): Initialize target descriptions. * linux-i386-ipa.c (idx2mask): New array. (get_ipa_tdesc): Move idx2mask out. (initialize_low_tracepoint): Initialize target descriptions. gdb/testsuite: 2017-12-07 Yao Qi <yao.qi@linaro.org> * gdb.trace/ftrace.exp (run_trace_experiment): Set breakpoint on malloc and catch syscall.
1 parent 30970df commit a880623

File tree

6 files changed

+81
-26
lines changed

6 files changed

+81
-26
lines changed

gdb/gdbserver/ChangeLog

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,14 @@
1+
2017-12-07 Yao Qi <yao.qi@linaro.org>
2+
3+
* linux-aarch64-ipa.c (initialize_low_tracepoint): Call
4+
aarch64_linux_read_description.
5+
* linux-amd64-ipa.c (idx2mask): New array.
6+
(get_ipa_tdesc): Move idx2mask out.
7+
(initialize_low_tracepoint): Initialize target descriptions.
8+
* linux-i386-ipa.c (idx2mask): New array.
9+
(get_ipa_tdesc): Move idx2mask out.
10+
(initialize_low_tracepoint): Initialize target descriptions.
11+
112
2017-12-05 Simon Marchi <simon.marchi@polymtl.ca>
213

314
* tdesc.c (struct tdesc_type): Change return type.

gdb/gdbserver/linux-aarch64-ipa.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -204,4 +204,5 @@ alloc_jump_pad_buffer (size_t size)
204204
void
205205
initialize_low_tracepoint (void)
206206
{
207+
aarch64_linux_read_description ();
207208
}

gdb/gdbserver/linux-amd64-ipa.c

Lines changed: 21 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -169,6 +169,19 @@ supply_static_tracepoint_registers (struct regcache *regcache,
169169

170170
#endif /* HAVE_UST */
171171

172+
#if !defined __ILP32__
173+
/* Map the tdesc index to xcr0 mask. */
174+
static uint64_t idx2mask[X86_TDESC_LAST] = {
175+
X86_XSTATE_X87_MASK,
176+
X86_XSTATE_SSE_MASK,
177+
X86_XSTATE_AVX_MASK,
178+
X86_XSTATE_MPX_MASK,
179+
X86_XSTATE_AVX_MPX_MASK,
180+
X86_XSTATE_AVX_AVX512_MASK,
181+
X86_XSTATE_AVX_MPX_AVX512_PKU_MASK,
182+
};
183+
#endif
184+
172185
/* Return target_desc to use for IPA, given the tdesc index passed by
173186
gdbserver. */
174187

@@ -194,17 +207,6 @@ get_ipa_tdesc (int idx)
194207
break;
195208
}
196209
#else
197-
/* Map the tdesc index to xcr0 mask. */
198-
uint64_t idx2mask[X86_TDESC_LAST] = {
199-
X86_XSTATE_X87_MASK,
200-
X86_XSTATE_SSE_MASK,
201-
X86_XSTATE_AVX_MASK,
202-
X86_XSTATE_MPX_MASK,
203-
X86_XSTATE_AVX_MPX_MASK,
204-
X86_XSTATE_AVX_AVX512_MASK,
205-
X86_XSTATE_AVX_MPX_AVX512_PKU_MASK,
206-
};
207-
208210
return amd64_linux_read_description (idx2mask[idx], false);
209211
#endif
210212

@@ -276,4 +278,12 @@ alloc_jump_pad_buffer (size_t size)
276278
void
277279
initialize_low_tracepoint (void)
278280
{
281+
#if defined __ILP32__
282+
amd64_linux_read_description (X86_XSTATE_SSE_MASK, true);
283+
amd64_linux_read_description (X86_XSTATE_AVX_MASK, true);
284+
amd64_linux_read_description (X86_XSTATE_AVX_AVX512_MASK, true);
285+
#else
286+
for (auto i = 0; i < X86_TDESC_LAST; i++)
287+
amd64_linux_read_description (idx2mask[i], false);
288+
#endif
279289
}

gdb/gdbserver/linux-i386-ipa.c

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -245,6 +245,17 @@ initialize_fast_tracepoint_trampoline_buffer (void)
245245
}
246246
}
247247

248+
/* Map the tdesc index to xcr0 mask. */
249+
static uint64_t idx2mask[X86_TDESC_LAST] = {
250+
X86_XSTATE_X87_MASK,
251+
X86_XSTATE_SSE_MASK,
252+
X86_XSTATE_AVX_MASK,
253+
X86_XSTATE_MPX_MASK,
254+
X86_XSTATE_AVX_MPX_MASK,
255+
X86_XSTATE_AVX_AVX512_MASK,
256+
X86_XSTATE_AVX_MPX_AVX512_PKU_MASK,
257+
};
258+
248259
/* Return target_desc to use for IPA, given the tdesc index passed by
249260
gdbserver. */
250261

@@ -256,18 +267,6 @@ get_ipa_tdesc (int idx)
256267
internal_error (__FILE__, __LINE__,
257268
"unknown ipa tdesc index: %d", idx);
258269
}
259-
260-
/* Map the tdesc index to xcr0 mask. */
261-
uint64_t idx2mask[X86_TDESC_LAST] = {
262-
X86_XSTATE_X87_MASK,
263-
X86_XSTATE_SSE_MASK,
264-
X86_XSTATE_AVX_MASK,
265-
X86_XSTATE_MPX_MASK,
266-
X86_XSTATE_AVX_MPX_MASK,
267-
X86_XSTATE_AVX_AVX512_MASK,
268-
X86_XSTATE_AVX_MPX_AVX512_PKU_MASK,
269-
};
270-
271270
return i386_linux_read_description (idx2mask[idx]);
272271
}
273272

@@ -290,4 +289,6 @@ void
290289
initialize_low_tracepoint (void)
291290
{
292291
initialize_fast_tracepoint_trampoline_buffer ();
292+
for (auto i = 0; i < X86_TDESC_LAST; i++)
293+
i386_linux_read_description (idx2mask[i]);
293294
}

gdb/testsuite/ChangeLog

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,8 @@
1+
2017-12-07 Yao Qi <yao.qi@linaro.org>
2+
3+
* gdb.trace/ftrace.exp (run_trace_experiment): Set breakpoint on
4+
malloc and catch syscall.
5+
16
2017-12-07 Phil Muldoon <pmuldoon@redhat.com>
27

38
* gdb.python/py-breakpoint.exp (test_bkpt_explicit_loc): Add new

gdb/testsuite/gdb.trace/ftrace.exp

Lines changed: 30 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -63,9 +63,36 @@ proc run_trace_experiment {} {
6363

6464
gdb_test_no_output "tstart" "start trace experiment"
6565

66-
gdb_test "continue" \
67-
".*Breakpoint \[0-9\]+, end .*" \
68-
"advance through tracing"
66+
# Fast tracepoint can be set in signal handler, so gdb_collect in
67+
# IPA shouldn't call any non-async-signal-safe functions. It is
68+
# impractical to list all non-async-signal-safe functions, and set
69+
# breakpoints on them, so choose malloc only in this test.
70+
gdb_test "b -q malloc"
71+
72+
# Performance-wise, gdb_collect in IPA shouldn't call any syscall
73+
# in order to keep fast tracepoint fast enough.
74+
global gdb_prompt
75+
set test "catch syscall"
76+
gdb_test_multiple $test $test {
77+
-re "The feature \'catch syscall\' is not supported.*\r\n$gdb_prompt $" {
78+
}
79+
-re ".*$gdb_prompt $" {
80+
pass $test
81+
}
82+
}
83+
84+
global decimal
85+
set test "advance through tracing"
86+
gdb_test_multiple "continue" $test {
87+
-re "Thread 2 .* hit Catchpoint $decimal \\(call to syscall .*\\).*\r\n$gdb_prompt $" {
88+
# IPA starts a helper thread, which calls accept. Ignore it.
89+
send_gdb "continue\n"
90+
exp_continue
91+
}
92+
-re "Breakpoint $decimal, end .*$gdb_prompt $" {
93+
pass $test
94+
}
95+
}
6996

7097
gdb_test "tstatus" ".*Trace .*" "check on trace status"
7198

0 commit comments

Comments
 (0)