Skip to content
Snippets Groups Projects
Commit cd93074e authored by rtm's avatar rtm
Browse files

LRU disk cache replacement

parent 22bac2cb
No related branches found
No related tags found
No related merge requests found
......@@ -357,3 +357,11 @@ OH! recursive interrupts will use up any amount of cpu[].stack!
better buffer cache replacement
read/write of open file that's been unlinked
disk scheduling
mkdir
more than one directory content block
sh arguments
sh redirection
indirect blocks
two bugs in unlink
how come unlink xxx fails? iput problem?
......@@ -10,27 +10,41 @@
struct buf buf[NBUF];
struct spinlock buf_table_lock;
// linked list of all buffers, through prev/next.
// bufhead->next is most recently used.
// bufhead->tail is least recently used.
struct buf bufhead;
void
binit(void)
{
struct buf *b;
initlock(&buf_table_lock, "buf_table");
bufhead.prev = &bufhead;
bufhead.next = &bufhead;
for(b = buf; b < buf+NBUF; b++){
b->next = bufhead.next;
b->prev = &bufhead;
bufhead.next->prev = b;
bufhead.next = b;
}
}
struct buf *
getblk(uint dev, uint sector)
{
struct buf *b;
static struct buf *scan = buf;
int i;
acquire(&buf_table_lock);
while(1){
for(b = buf; b < buf+NBUF; b++)
for(b = bufhead.next; b != &bufhead; b = b->next)
if((b->flags & (B_BUSY|B_VALID)) && b->dev == dev && b->sector == sector)
break;
if(b < buf+NBUF){
if(b != &bufhead){
if(b->flags & B_BUSY){
sleep(buf, &buf_table_lock);
} else {
......@@ -39,10 +53,7 @@ getblk(uint dev, uint sector)
return b;
}
} else {
for(i = 0; i < NBUF; i++){
b = scan++;
if(scan >= buf+NBUF)
scan = buf;
for(b = bufhead.prev; b != &bufhead; b = b->prev){
if((b->flags & B_BUSY) == 0){
b->flags = B_BUSY;
b->dev = dev;
......@@ -64,8 +75,9 @@ bread(uint dev, uint sector)
extern struct spinlock ide_lock;
b = getblk(dev, sector);
if(b->flags & B_VALID)
if(b->flags & B_VALID){
return b;
}
acquire(&ide_lock);
c = ide_start_rw(dev & 0xff, sector, b->data, 1, 1);
......@@ -99,6 +111,13 @@ brelse(struct buf *b)
acquire(&buf_table_lock);
b->next->prev = b->prev;
b->prev->next = b->next;
b->next = bufhead.next;
b->prev = &bufhead;
bufhead.next->prev = b;
bufhead.next = b;
b->flags &= ~B_BUSY;
wakeup(buf);
......
......@@ -2,6 +2,8 @@ struct buf {
int flags;
uint dev;
uint sector;
struct buf *prev;
struct buf *next;
uchar data[512];
};
#define B_BUSY 0x1
......
......@@ -505,7 +505,7 @@ unlink(char *cp)
if ((ip = namei(cp, &pinum)) == 0) {
cprintf("file to be unlinked doesn't exist\n");
cprintf("unlink(%s) it doesn't exist\n", cp);
return -1;
}
......
......@@ -303,7 +303,7 @@ createdelete()
void
unlinkread()
{
int fd;
int fd, fd1;
fd = open("unlinkread", O_CREATE | O_RDWR);
if(fd < 0){
......@@ -322,15 +322,25 @@ unlinkread()
puts("unlink unlinkread failed\n");
exit();
}
fd1 = open("xxx", O_CREATE | O_RDWR);
write(fd1, "yyy", 3);
close(fd1);
if(read(fd, buf, sizeof(buf)) != 5){
puts("unlinkread read failed");
exit();
}
if(buf[0] != 'h'){
puts("unlinkread wrong data\n");
exit();
}
if(write(fd, buf, 10) != 10){
puts("unlinkread write failed\n");
exit();
}
close(fd);
unlink("xxx");
puts("unlinkread ok\n");
}
......@@ -339,7 +349,7 @@ main(int argc, char *argv[])
{
puts("usertests starting\n");
//unlinkread();
unlinkread();
createdelete();
twofiles();
sharedfd();
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment