mirror of
https://github.com/netbirdio/gvisor.git
synced 2026-05-22 17:12:49 -07:00
kernel: hold TaskSet mutex across exitPtrace() and exitChildren()
This just saves needlessly bouncing the mutex. Compare Linux kernel/exit.c:exit_notify() => write_lock_irq(&tasklist_lock); forget_original_parent() => exit_ptrace(). PiperOrigin-RevId: 681181467
This commit is contained in:
@@ -567,10 +567,10 @@ func (t *Task) ptraceDetach(target *Task, sig linux.Signal) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// exitPtrace is called in the exit path to detach all of t's tracees.
|
||||
func (t *Task) exitPtrace() {
|
||||
t.tg.pidns.owner.mu.Lock()
|
||||
defer t.tg.pidns.owner.mu.Unlock()
|
||||
// exitPtraceLocked is called in the exit path to detach all of t's tracees.
|
||||
//
|
||||
// Preconditions: The TaskSet mutex must be locked for writing.
|
||||
func (t *Task) exitPtraceLocked() {
|
||||
for target := range t.ptraceTracees {
|
||||
if target.ptraceOpts.ExitKill {
|
||||
target.tg.signalHandlers.mu.Lock()
|
||||
|
||||
@@ -315,14 +315,15 @@ func (*runExitMain) execute(t *Task) taskRunState {
|
||||
t.tg.Release(t)
|
||||
}
|
||||
|
||||
t.tg.pidns.owner.mu.Lock()
|
||||
// Detach tracees.
|
||||
t.exitPtrace()
|
||||
|
||||
t.exitPtraceLocked()
|
||||
// Reparent the task's children.
|
||||
t.exitChildren()
|
||||
t.exitChildrenLocked()
|
||||
t.tg.pidns.owner.mu.Unlock()
|
||||
|
||||
// Don't tail-call runExitNotify, as exitChildren may have initiated a stop
|
||||
// to wait for a PID namespace to die.
|
||||
// Don't tail-call runExitNotify, as exitChildrenLocked may have initiated
|
||||
// a stop to wait for a PID namespace to die.
|
||||
return (*runExitNotify)(nil)
|
||||
}
|
||||
|
||||
@@ -360,9 +361,8 @@ func (t *Task) exitThreadGroup() bool {
|
||||
return last
|
||||
}
|
||||
|
||||
func (t *Task) exitChildren() {
|
||||
t.tg.pidns.owner.mu.Lock()
|
||||
defer t.tg.pidns.owner.mu.Unlock()
|
||||
// Preconditions: The TaskSet mutex must be locked for writing.
|
||||
func (t *Task) exitChildrenLocked() {
|
||||
newParent := t.findReparentTargetLocked()
|
||||
if newParent == nil {
|
||||
// "If the init process of a PID namespace terminates, the kernel
|
||||
|
||||
Reference in New Issue
Block a user