Skip to content

Commit

Permalink
change allocproc() back to acquiring the ptable.lock.
Browse files Browse the repository at this point in the history
fix bugs where caller incorrectly released lock on error return path.
  • Loading branch information
Robert Morris committed Sep 15, 2016
1 parent 469aa8b commit aeaa308
Showing 1 changed file with 6 additions and 14 deletions.
20 changes: 6 additions & 14 deletions proc.c
Original file line number Diff line number Diff line change
Expand Up @@ -31,22 +31,27 @@ pinit(void)
// If found, change state to EMBRYO and initialize
// state required to run in the kernel.
// Otherwise return 0.
// Must hold ptable.lock.
static struct proc*
allocproc(void)
{
struct proc *p;
char *sp;

acquire(&ptable.lock);

for(p = ptable.proc; p < &ptable.proc[NPROC]; p++)
if(p->state == UNUSED)
goto found;

release(&ptable.lock);
return 0;

found:
p->state = EMBRYO;
p->pid = nextpid++;

release(&ptable.lock);

// Allocate kernel stack.
if((p->kstack = kalloc()) == 0){
p->state = UNUSED;
Expand Down Expand Up @@ -79,14 +84,7 @@ userinit(void)
struct proc *p;
extern char _binary_initcode_start[], _binary_initcode_size[];

acquire(&ptable.lock);

p = allocproc();

// release the lock in case namei() sleeps.
// the lock isn't needed because no other
// thread will look at an EMBRYO proc.
release(&ptable.lock);

initproc = p;
if((p->pgdir = setupkvm()) == 0)
Expand Down Expand Up @@ -145,22 +143,16 @@ fork(void)
int i, pid;
struct proc *np;

acquire(&ptable.lock);

// Allocate process.
if((np = allocproc()) == 0){
release(&ptable.lock);
return -1;
}

release(&ptable.lock);

// Copy process state from p.
if((np->pgdir = copyuvm(proc->pgdir, proc->sz)) == 0){
kfree(np->kstack);
np->kstack = 0;
np->state = UNUSED;
release(&ptable.lock);
return -1;
}
np->sz = proc->sz;
Expand Down

0 comments on commit aeaa308

Please sign in to comment.