summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--file.h4
-rw-r--r--fs.c18
2 files changed, 12 insertions, 10 deletions
diff --git a/file.h b/file.h
index 73a8e67..497a58a 100644
--- a/file.h
+++ b/file.h
@@ -14,8 +14,8 @@ struct inode {
uint dev; // Device number
uint inum; // Inode number
int ref; // Reference count
- struct sleeplock lock;
- int valid; // remainder has been read from disk?
+ struct sleeplock lock; // protects everything below here
+ int valid; // inode has been read from disk?
short type; // copy of disk inode
short major;
diff --git a/fs.c b/fs.c
index b67db5d..c73c530 100644
--- a/fs.c
+++ b/fs.c
@@ -320,15 +320,17 @@ void
iput(struct inode *ip)
{
acquire(&icache.lock);
- if(ip->ref == 1 && ip->valid && ip->nlink == 0){
- // inode has no links and no other references: truncate and free.
+ if(ip->ref == 1){
acquiresleep(&ip->lock);
- release(&icache.lock);
- itrunc(ip);
- ip->type = 0;
- iupdate(ip);
- acquire(&icache.lock);
- ip->valid = 0;
+ if(ip->valid && ip->nlink == 0){
+ // inode has no links and no other references: truncate and free.
+ release(&icache.lock);
+ itrunc(ip);
+ ip->type = 0;
+ iupdate(ip);
+ ip->valid = 0;
+ acquire(&icache.lock);
+ }
releasesleep(&ip->lock);
}
ip->ref--;