Skip to content

Commit 0995536

Browse files
ivanivanov884jeffmahoney
authored andcommitted
gdb-gnat-dwarf-crash-3of3.patch
;; Fix crash of -readnow /usr/lib/debug/usr/bin/gnatbind.debug (BZ 1069211). ;;=push+jan http://sourceware.org/ml/gdb-patches/2014-02/msg00731.html --6TrnltStXW4iwmi0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Hi, PR 16581: GDB crash on inherit_abstract_dies infinite recursion https://sourceware.org/bugzilla/show_bug.cgi?id=16581 fixed crash from an infinite recursion. But in rare cases the new code can now gdb_assert() due to weird DWARF file. I do not yet fully understand why the DWARF is as it is but just GDB should never crash due to invalid DWARF anyway. The "invalid" DWARF I see only in Fedora GCC build, not in FSF GCC build, more info at: https://bugzilla.redhat.com/show_bug.cgi?id=1069382 http://people.redhat.com/jkratoch/gcc-debuginfo-4.8.2-7.fc20.x86_64-gnatbind.debug Thanks, Jan --6TrnltStXW4iwmi0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline; filename="complaint.patch" gdb/ 2014-02-24 Jan Kratochvil <[email protected]> * dwarf2read.c (process_die): Change gdb_assert to complaint.
1 parent b3a7e59 commit 0995536

File tree

4 files changed

+119
-1
lines changed

4 files changed

+119
-1
lines changed

gdb/dwarf2read.c

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10499,6 +10499,13 @@ class process_die_scope
1049910499
static void
1050010500
process_die (struct die_info *die, struct dwarf2_cu *cu)
1050110501
{
10502+
if (die->in_process)
10503+
{
10504+
complaint (_("DIE at 0x%s attempted to be processed twice"),
10505+
sect_offset_str (die->sect_off));
10506+
return;
10507+
}
10508+
1050210509
process_die_scope scope (die, cu);
1050310510

1050410511
switch (die->tag)

gdb/infrun.c

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -607,6 +607,13 @@ holding the child stopped. Try \"set detach-on-fork\" or \
607607
target_pid_to_str (process_ptid));
608608
}
609609

610+
#ifdef NEED_DETACH_SIGSTOP
611+
/* We should check PID_WAS_STOPPED and detach it stopped accordingly.
612+
In this point of code it cannot be 1 as we would not get FORK
613+
executed without CONTINUE first which resets PID_WAS_STOPPED.
614+
We would have to first TARGET_STOP and WAITPID it as with running
615+
inferior PTRACE_DETACH, SIGSTOP will ignore the signal. */
616+
#endif
610617
target_detach (parent_inf, 0);
611618
}
612619

gdb/linux-nat.c

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -191,6 +191,12 @@ struct linux_nat_target *linux_target;
191191
/* Does the current host support PTRACE_GETREGSET? */
192192
enum tribool have_ptrace_getregset = TRIBOOL_UNKNOWN;
193193

194+
#ifdef NEED_DETACH_SIGSTOP
195+
/* PID of the inferior stopped by SIGSTOP before attaching (or zero). */
196+
static pid_t pid_was_stopped;
197+
198+
#endif
199+
194200
/* The saved to_close method, inherited from inf-ptrace.c.
195201
Called by our to_close. */
196202
static void (*super_close) (struct target_ops *);
@@ -1027,6 +1033,9 @@ linux_nat_post_attach_wait (ptid_t ptid, int *signalled)
10271033
if (debug_linux_nat)
10281034
fprintf_unfiltered (gdb_stdlog,
10291035
"LNPAW: Attaching to a stopped process\n");
1036+
#ifdef NEED_DETACH_SIGSTOP
1037+
pid_was_stopped = ptid.pid ();
1038+
#endif
10301039

10311040
/* The process is definitely stopped. It is in a job control
10321041
stop, unless the kernel predates the TASK_STOPPED /
@@ -1359,6 +1368,25 @@ get_detach_signal (struct lwp_info *lp)
13591368
return gdb_signal_to_host (signo);
13601369
}
13611370

1371+
#ifdef NEED_DETACH_SIGSTOP
1372+
/* Workaround RHEL-5 kernel which has unreliable PTRACE_DETACH, SIGSTOP (that
1373+
many TIDs are left unstopped). See RH Bug 496732. */
1374+
if (lp->ptid.pid () == pid_was_stopped)
1375+
{
1376+
int err;
1377+
1378+
errno = 0;
1379+
err = kill_lwp (lp->ptid.lwp (), SIGSTOP);
1380+
if (debug_linux_nat)
1381+
{
1382+
fprintf_unfiltered (gdb_stdlog,
1383+
"SC: lwp kill %d %s\n",
1384+
err,
1385+
errno ? safe_strerror (errno) : "ERRNO-OK");
1386+
}
1387+
}
1388+
1389+
#endif
13621390
return 0;
13631391
}
13641392

@@ -1507,6 +1535,10 @@ linux_nat_target::detach (inferior *inf, int from_tty)
15071535
detach_one_lwp (main_lwp, &signo);
15081536

15091537
detach_success (inf);
1538+
1539+
#ifdef NEED_DETACH_SIGSTOP
1540+
pid_was_stopped = 0;
1541+
#endif
15101542
}
15111543
}
15121544

@@ -1765,6 +1797,16 @@ linux_nat_target::resume (ptid_t ptid, int step, enum gdb_signal signo)
17651797
return;
17661798
}
17671799

1800+
#ifdef NEED_DETACH_SIGSTOP
1801+
/* At this point, we are going to resume the inferior and if we
1802+
have attached to a stopped process, we no longer should leave
1803+
it as stopped if the user detaches. PTID variable has PID set to LWP
1804+
while we need to check the real PID here. */
1805+
1806+
if (!step && lp && pid_was_stopped == lp->ptid.pid ())
1807+
pid_was_stopped = 0;
1808+
1809+
#endif
17681810
if (resume_many)
17691811
iterate_over_lwps (ptid, linux_nat_resume_callback, lp);
17701812

@@ -3761,6 +3803,10 @@ linux_nat_target::mourn_inferior ()
37613803

37623804
/* Let the arch-specific native code know this process is gone. */
37633805
linux_target->low_forget_process (pid);
3806+
#ifdef NEED_DETACH_SIGSTOP
3807+
3808+
pid_was_stopped = 0;
3809+
#endif
37643810
}
37653811

37663812
/* Convert a native/host siginfo object, into/from the siginfo in the

gdb/testsuite/gdb.threads/attach-stopped.exp

Lines changed: 59 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,65 @@ proc corefunc { threadtype } {
5656
gdb_reinitialize_dir $srcdir/$subdir
5757
gdb_load ${binfile}
5858

59-
# Verify that we can attach to the stopped process.
59+
# Verify that we can attach to the process by first giving its
60+
# executable name via the file command, and using attach with the
61+
# process ID.
62+
63+
set test "$threadtype: set file, before attach1 to stopped process"
64+
gdb_test_multiple "file $binfile" "$test" {
65+
-re "Load new symbol table from.*y or n. $" {
66+
gdb_test "y" "Reading symbols from $escapedbinfile\.\.\.*done." \
67+
"$test (re-read)"
68+
}
69+
-re "Reading symbols from $escapedbinfile\.\.\.*done.*$gdb_prompt $" {
70+
pass "$test"
71+
}
72+
}
73+
74+
set test "$threadtype: attach1 to stopped, after setting file"
75+
gdb_test_multiple "attach $testpid" "$test" {
76+
-re "Attaching to program.*`?$escapedbinfile'?, process $testpid.*$gdb_prompt $" {
77+
pass "$test"
78+
}
79+
}
80+
81+
# ".*sleep.*clone.*" would fail on s390x as bt stops at START_THREAD there.
82+
if {[string equal $threadtype threaded]} {
83+
gdb_test "thread apply all bt" ".*sleep.*start_thread.*" "$threadtype: attach1 to stopped bt"
84+
} else {
85+
gdb_test "bt" ".*sleep.*main.*" "$threadtype: attach1 to stopped bt"
86+
}
87+
88+
# Exit and detach the process.
89+
90+
gdb_exit
91+
92+
# Avoid some race:
93+
sleep 2
94+
95+
if [catch {open /proc/${testpid}/status r} fileid] {
96+
set line2 "NOTFOUND"
97+
} else {
98+
gets $fileid line1;
99+
gets $fileid line2;
100+
close $fileid;
101+
}
102+
103+
set test "$threadtype: attach1, exit leaves process stopped"
104+
if {[string match "*(stopped)*" $line2]} {
105+
pass $test
106+
} else {
107+
fail $test
108+
}
109+
110+
# At this point, the process should still be stopped
111+
112+
gdb_start
113+
gdb_reinitialize_dir $srcdir/$subdir
114+
gdb_load ${binfile}
115+
116+
# Verify that we can attach to the process just by giving the
117+
# process ID.
60118

61119
set test "$threadtype: attach2 to stopped, after setting file"
62120
gdb_test_multiple "attach $testpid" "$test" {

0 commit comments

Comments
 (0)