/* program to implement Least Recently Used (LRU) Cache */
#include<stdio.h>
#include<stdlib.h>
// define node for doubly linked list holds pageNumber
typedef struct QNode
{
struct QNode *prev, *next;
unsigned int pageNumber;
} QNode;
// Queue - collection of QNodes
typedef struct Queue
{
unsigned count;
unsigned numberofFrames;
QNode *front, *rear;
} Queue;
// hash as collection of pointers to Qnodes and size
typedef struct Hash
{
int capacity;
QNode* *array;
}Hash;
QNode* createQNode(int pageNumber)
{
QNode* qNode = (QNode*) malloc (sizeof(QNode));
qNode->pageNumber = pageNumber;
qNode->prev = qNode->next = NULL;
return qNode;
}
Queue* createQueue(int numberofFrames)
{
Queue* queue = (Queue*) malloc (sizeof(Queue));
queue->count = 0;
queue->front = queue->rear = NULL;
queue->numberofFrames = numberofFrames;
return queue;
}
Hash* createHash(int capacity)
{
Hash *hash = (Hash*) malloc (sizeof(Hash));
hash->capacity = capacity;
hash->array = (QNode**) malloc( hash->capacity * sizeof(QNode*));
int i;
for(i =0; i< hash->capacity;++i)
hash->array[i] = NULL;
return hash;
}
void deQueue (Queue* queue) {
if (queue->count == 0)
return ;
if (queue->front == queue->rear)
queue->front = queue->rear = NULL;
QNode* temp = queue->rear;
queue->rear = queue->rear->prev;
if(queue->rear)
queue->rear->next = NULL;
free(temp);
if (queue->count > 0)
queue->count--;
}
void Enqueue (Queue* queue, Hash* hash, unsigned pageNumber)
{
if (queue->count == queue->numberofFrames) {
hash->array[queue->rear->pageNumber] = NULL;
deQueue(queue);
}
QNode* temp = createQNode(pageNumber);
temp->next = queue->front;
if (queue->count == 0) {
queue->rear = queue->front = temp;
} else {
queue->front->prev = temp;
queue->front = temp;
}
hash->array[pageNumber] = temp;
queue->count++;
}
// when a page with pageNumber is referenced from cache:
// 1) frame is not present in memory,which needs to be added
//in memory (add at front of queue)
// 2) if page is present with given page number then needs to
// be moved to the front of queue.
void ReferencePage(Queue* queue, Hash* hash, unsigned pageNumber)
{
QNode* reqPage = hash->array[pageNumber];
// page is not in cache, add to the queue
if (reqPage == NULL)
Enqueue( queue, hash, pageNumber);
// page is there and not at front, need to move to front
else if (reqPage != queue->front) {
reqPage->prev->next = reqPage->next;
if (reqPage->next)
reqPage->next->prev = reqPage->prev;
if(reqPage == queue->rear)
{
queue->rear = reqPage->prev;
queue->rear->next = NULL;
}
reqPage->next = queue->front;
reqPage->prev = NULL;
reqPage->next->prev = reqPage;
queue->front = reqPage;
}
}
int main()
{
// create a queue for number of pages to be hold by cache
Queue* q = createQueue(4); // 4 pages
// create hash to reference pages
Hash* hash = createHash(10);
ReferencePage( q, hash, 1);
ReferencePage( q, hash, 2);
ReferencePage( q, hash, 3);
ReferencePage (q, hash, 1);
ReferencePage (q, hash, 4);
ReferencePage (q, hash, 5);
// print the cache page frames after the referencing
printf ("%d", q->front->pageNumber);
printf("%d", q->front->next->pageNumber);
printf("%d", q->front->next->next->pageNumber);
printf("%d\n", q->front->next->next->next->pageNumber);
return 0;
}
#include<stdio.h>
#include<stdlib.h>
// define node for doubly linked list holds pageNumber
typedef struct QNode
{
struct QNode *prev, *next;
unsigned int pageNumber;
} QNode;
// Queue - collection of QNodes
typedef struct Queue
{
unsigned count;
unsigned numberofFrames;
QNode *front, *rear;
} Queue;
// hash as collection of pointers to Qnodes and size
typedef struct Hash
{
int capacity;
QNode* *array;
}Hash;
QNode* createQNode(int pageNumber)
{
QNode* qNode = (QNode*) malloc (sizeof(QNode));
qNode->pageNumber = pageNumber;
qNode->prev = qNode->next = NULL;
return qNode;
}
Queue* createQueue(int numberofFrames)
{
Queue* queue = (Queue*) malloc (sizeof(Queue));
queue->count = 0;
queue->front = queue->rear = NULL;
queue->numberofFrames = numberofFrames;
return queue;
}
Hash* createHash(int capacity)
{
Hash *hash = (Hash*) malloc (sizeof(Hash));
hash->capacity = capacity;
hash->array = (QNode**) malloc( hash->capacity * sizeof(QNode*));
int i;
for(i =0; i< hash->capacity;++i)
hash->array[i] = NULL;
return hash;
}
void deQueue (Queue* queue) {
if (queue->count == 0)
return ;
if (queue->front == queue->rear)
queue->front = queue->rear = NULL;
QNode* temp = queue->rear;
queue->rear = queue->rear->prev;
if(queue->rear)
queue->rear->next = NULL;
free(temp);
if (queue->count > 0)
queue->count--;
}
void Enqueue (Queue* queue, Hash* hash, unsigned pageNumber)
{
if (queue->count == queue->numberofFrames) {
hash->array[queue->rear->pageNumber] = NULL;
deQueue(queue);
}
QNode* temp = createQNode(pageNumber);
temp->next = queue->front;
if (queue->count == 0) {
queue->rear = queue->front = temp;
} else {
queue->front->prev = temp;
queue->front = temp;
}
hash->array[pageNumber] = temp;
queue->count++;
}
// when a page with pageNumber is referenced from cache:
// 1) frame is not present in memory,which needs to be added
//in memory (add at front of queue)
// 2) if page is present with given page number then needs to
// be moved to the front of queue.
void ReferencePage(Queue* queue, Hash* hash, unsigned pageNumber)
{
QNode* reqPage = hash->array[pageNumber];
// page is not in cache, add to the queue
if (reqPage == NULL)
Enqueue( queue, hash, pageNumber);
// page is there and not at front, need to move to front
else if (reqPage != queue->front) {
reqPage->prev->next = reqPage->next;
if (reqPage->next)
reqPage->next->prev = reqPage->prev;
if(reqPage == queue->rear)
{
queue->rear = reqPage->prev;
queue->rear->next = NULL;
}
reqPage->next = queue->front;
reqPage->prev = NULL;
reqPage->next->prev = reqPage;
queue->front = reqPage;
}
}
int main()
{
// create a queue for number of pages to be hold by cache
Queue* q = createQueue(4); // 4 pages
// create hash to reference pages
Hash* hash = createHash(10);
ReferencePage( q, hash, 1);
ReferencePage( q, hash, 2);
ReferencePage( q, hash, 3);
ReferencePage (q, hash, 1);
ReferencePage (q, hash, 4);
ReferencePage (q, hash, 5);
// print the cache page frames after the referencing
printf ("%d", q->front->pageNumber);
printf("%d", q->front->next->pageNumber);
printf("%d", q->front->next->next->pageNumber);
printf("%d\n", q->front->next->next->next->pageNumber);
return 0;
}
No comments:
Post a Comment