* process.c: Add a comment. No code changes.
* strace.c (collect_stopped_tcbs): Stop reversing list of stopped
tcp's. I'm not totally convinced it is crucial, but this is surely
fits the concept of "least surprise".
Do not collect TCB_SUSPENDED tcp's (this is closer to how
it was before).
(handle_stopped_tcbs): Remove the code to reject TCB_SUSPENDED tcp's,
it's done earlier now. In an unobvious way, this was causing
SIGSTOPs from freshly attached children to be misinterpreted.
diff --git a/strace.c b/strace.c
index 57945db..80d468a 100644
--- a/strace.c
+++ b/strace.c
@@ -2279,7 +2279,8 @@
struct rusage ru;
struct rusage* ru_ptr = cflag ? &ru : NULL;
int wnohang = 0;
- struct tcb *found_tcps = NULL;
+ struct tcb *found_tcps;
+ struct tcb **nextp = &found_tcps;
#ifdef __WALL
int wait4_options = __WALL;
#endif
@@ -2401,30 +2402,6 @@
tcp->stime = ru.ru_stime;
#endif
}
- tcp->wait_status = status;
-#ifdef LINUX
- tcp->next_need_service = found_tcps;
- found_tcps = tcp;
- wnohang = WNOHANG;
-#endif
-#ifdef SUNOS4
- /* Probably need to replace wait with waitpid
- * and loop on Sun too, but I can't test it. Volunteers?
- */
- break;
-#endif
- } /* while (1) - collecting all stopped/exited tracees */
-
- return tcp;
-}
-
-static int
-handle_stopped_tcbs(struct tcb *tcp)
-{
- for (; tcp; tcp = tcp->next_need_service) {
- int pid;
- int status;
-
if (tcp->flags & TCB_SUSPENDED) {
/*
* Apparently, doing any ptrace() call on a stopped
@@ -2437,6 +2414,37 @@
continue;
}
+ tcp->wait_status = status;
+#ifdef LINUX
+ /* It is important to not invert the order of tasks
+ * to process. For one, alloc_tcb() above picks newly forked
+ * threads in some order, processing of them and their parent
+ * should be in the same order, otherwise bad things happen
+ * (misinterpreted SIGSTOPs and such).
+ */
+ *nextp = tcp;
+ nextp = &tcp->next_need_service;
+ wnohang = WNOHANG;
+#endif
+#ifdef SUNOS4
+ /* Probably need to replace wait with waitpid
+ * and loop on Sun too, but I can't test it. Volunteers?
+ */
+ break;
+#endif
+ }
+
+ *nextp = NULL;
+ return found_tcps;
+}
+
+static int
+handle_stopped_tcbs(struct tcb *tcp)
+{
+ for (; tcp; tcp = tcp->next_need_service) {
+ int pid;
+ int status;
+
outf = tcp->outf;
status = tcp->wait_status;
pid = tcp->pid;