summaryrefslogtreecommitdiff
path: root/kernel
diff options
context:
space:
mode:
authorRobert Morris <[email protected]>2019-07-07 06:39:58 -0400
committerRobert Morris <[email protected]>2019-07-07 06:39:58 -0400
commit7114bf43ed4bfcfd5534a2aa722c2778501ae2b3 (patch)
tree38425f6bc3c2a942ffa5cff5ac53fccf175b56fe /kernel
parent62313be582a5abd3a114eec3c9f5770ea37ef766 (diff)
parentdabbc348bc4edab522901d8473acaabe276cdc45 (diff)
downloadxv6-labs-7114bf43ed4bfcfd5534a2aa722c2778501ae2b3.tar.gz
xv6-labs-7114bf43ed4bfcfd5534a2aa722c2778501ae2b3.tar.bz2
xv6-labs-7114bf43ed4bfcfd5534a2aa722c2778501ae2b3.zip
Merge branch 'riscv-proc' of g.csail.mit.edu:xv6-dev into riscv-proc
Diffstat (limited to 'kernel')
-rw-r--r--kernel/proc.c32
1 files changed, 20 insertions, 12 deletions
diff --git a/kernel/proc.c b/kernel/proc.c
index 9c64c4a..2266ca6 100644
--- a/kernel/proc.c
+++ b/kernel/proc.c
@@ -288,22 +288,28 @@ fork(void)
return pid;
}
-// Pass p's abandoned children to init.
-void reparent(struct proc *p) {
+// Pass p's abandoned children to init. p and p's parent
+// are locked.
+void reparent(struct proc *p, struct proc *parent) {
struct proc *pp;
for(pp = ptable.proc; pp < &ptable.proc[NPROC]; pp++){
- acquire(&pp->lock);
- if(pp->parent == p){
- pp->parent = initproc;
- if(pp->state == ZOMBIE) {
+ if (pp != p && pp != parent) {
+ acquire(&pp->lock);
+ if(pp->parent == p){
+ pp->parent = initproc;
+ if(pp->state == ZOMBIE) {
+ acquire(&initproc->lock);
wakeup1(initproc);
+ release(&initproc->lock);
+ }
}
+ release(&pp->lock);
}
- release(&pp->lock);
}
}
+
// Exit the current process. Does not return.
// An exited process remains in the zombie state
// until its parent calls wait().
@@ -331,19 +337,20 @@ exit(void)
iput(cwd);
end_op();
- reparent(p);
-
acquire(&p->parent->lock);
acquire(&p->lock);
+
+ reparent(p, p->parent);
+
p->cwd = 0;
p->state = ZOMBIE;
- release(&p->parent->lock);
-
// Parent might be sleeping in wait().
wakeup1(p->parent);
+ release(&p->parent->lock);
+
// Jump into the scheduler, never to return.
sched();
panic("zombie exit");
@@ -529,7 +536,8 @@ sleep(void *chan, struct spinlock *lk)
}
//PAGEBREAK!
-// Wake up locked parent, used by exit()
+// Wake up p, used by exit()
+// Caller should lock p.
static void
wakeup1(struct proc *p)
{