From f6878f47e29001491e902f03fbe4ff6ba8b3b4db Mon Sep 17 00:00:00 2001 From: Andrew Kolumbic Date: Wed, 22 Aug 2018 11:15:35 -0700 Subject: [PATCH 1/5] initial commit --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index 0660c39..65ae91d 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,6 @@ # Multi-Level Feedback Queue + ### Motivation After talking about one of the most popular scheduling algorithms used by operating systems to schedule processes, let's implement it! This will be an implementation that simulates an actual multi-level feedback queue processing From 9388fd0a5cea8ca8b554df78cb0bd8c36a407994 Mon Sep 17 00:00:00 2001 From: Andrew Kolumbic Date: Wed, 22 Aug 2018 14:45:20 -0700 Subject: [PATCH 2/5] process passing -still need to add comments --- src/Process.js | 24 +++++++++++++++++++----- 1 file changed, 19 insertions(+), 5 deletions(-) diff --git a/src/Process.js b/src/Process.js index 159a307..001e951 100644 --- a/src/Process.js +++ b/src/Process.js @@ -16,11 +16,11 @@ class Process { } setParentQueue(queue) { - + this.queue = queue; } isFinished() { - + return this.cpuTimeNeeded === 0 && this.blockingTimeNeeded === 0; } // If no blocking time is needed by this process, decrement the amount of @@ -29,7 +29,15 @@ class Process { // by emitting the appropriate interrupt // Make sure the `stateChanged` flag is toggled appropriately executeProcess(time) { - + this.stateChanged = false; + if (this.blockingTimeNeeded === 0) { + this.cpuTimeNeeded -= time; + // if we get a negative value, its 0 + this.cpuTimeNeeded = this.cpuTimeNeeded > 0 ? this.cpuTimeNeeded : 0; + } else { + this.queue.emitInterrupt(this, SchedulerInterrupt.PROCESS_BLOCKED); + this.stateChanged = true; + } } // If this process requires blocking time, decrement the amount of blocking @@ -38,16 +46,22 @@ class Process { // top running queue by emitting the appropriate interrupt // Make sure the `stateChanged` flag is toggled appropriately executeBlockingProcess(time) { + this.blockingTimeNeeded -= time; + this.blockingTimeNeeded = this.blockingTimeNeeded > 0 ? this.blockingTimeNeeded : 0; + if (this.blockingTimeNeeded === 0) { + this.queue.emitInterrupt(this, SchedulerInterrupt.PROCESS_READY); + this.stateChanged = true; + } } // Returns this process's stateChanged property isStateChanged() { - + return this.stateChanged; } get pid() { - + return this._pid; } // Private function used for testing; DO NOT MODIFY From 51c72e7ae7178971f642162cea73617744c2488e Mon Sep 17 00:00:00 2001 From: Andrew Kolumbic Date: Wed, 22 Aug 2018 16:04:24 -0700 Subject: [PATCH 3/5] Queue.js NOT PASSING --- src/Queue.js | 43 ++++++++++++++++++++++++++++++++++--------- 1 file changed, 34 insertions(+), 9 deletions(-) diff --git a/src/Queue.js b/src/Queue.js index 7b45fdf..3f97a65 100644 --- a/src/Queue.js +++ b/src/Queue.js @@ -19,29 +19,31 @@ class Queue { // Enqueues the given process. Return the enqueue'd process enqueue(process) { - + process.setParentQueue(this); + this.processes.push(process); + return process; } // Dequeues the next process in the queue. Return the dequeue'd process dequeue() { - + return this.processes.shift(); } // Return the least-recently added process without removing it from the list of processes peek() { - + return this.processes[0]; } isEmpty() { - + return this.processes.length === 0; } getPriorityLevel() { - + return this.priorityLevel; } getQueueType() { - + return this.queueType; } // Manages a process's execution for the given amount of time @@ -49,26 +51,49 @@ class Queue { // Once a process has received the alloted time, it needs to be dequeue'd and // then handled accordingly, depending on whether it has finished executing or not manageTimeSlice(currentProcess, time) { + if (currentProcess.isStateChanged()) { + this.quantumClock = 0; + return; + } + + this.quantumClock += time; + + if (this.quantumClock >= this.quantum) { + this.quantumClock = 0; + const process = this.dequeue(); + + if (!process.isFinished()) { + this.scheduler.handleInterrupt(this, process, SchedulerInterrupt) + } + } } // Execute the next non-blocking process (assuming this is a CPU queue) // This method should call `manageTimeSlice` as well as execute the next running process doCPUWork(time) { - + const process = this.peek(); + process.executeProcess(time); + this.manageTimeSlice(process, time); } // Execute the next blocking process (assuming this is the blocking queue) // This method should call `manageTimeSlice` as well as execute the next blocking process doBlockingWork(time) { - + const process = this.peek(); + process.executeBlockingProcess(time); + this.manageTimeSlice(process, time); } // The queue's interrupt handler for notifying when a process needs to be moved to a different queue // Should handle PROCESS_BLOCKED and PROCESS_READY interrupts // The process also needs to be removed from the queue emitInterrupt(source, interrupt) { - + const sourceIndex = this.processes.indexOf(source); + console.log("LOOK HERE:", sourceIndex); + console.log(this.processes) + this.processess.splice(sourceIndex, 1); + this.scheduler.handleInterrupt(this, source, interrupt); } } From 6c74571e02f576c1590ff91cd023207253c961d2 Mon Sep 17 00:00:00 2001 From: Andrew Kolumbic Date: Thu, 23 Aug 2018 09:41:34 -0700 Subject: [PATCH 4/5] scheduler (NOT PASSING) -queue is passing now, I had a typo -Scheduler is having weird behavior with the break[ln 46] -test won't run with it, but fails because its not there when removed -im leaving it commented out to show its the only failing test --- src/Queue.js | 6 +++--- src/Scheduler.js | 43 ++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 43 insertions(+), 6 deletions(-) diff --git a/src/Queue.js b/src/Queue.js index 3f97a65..fa6a1e0 100644 --- a/src/Queue.js +++ b/src/Queue.js @@ -90,9 +90,9 @@ class Queue { // The process also needs to be removed from the queue emitInterrupt(source, interrupt) { const sourceIndex = this.processes.indexOf(source); - console.log("LOOK HERE:", sourceIndex); - console.log(this.processes) - this.processess.splice(sourceIndex, 1); + // console.log("LOOK HERE:", sourceIndex); + // console.log(this.processes) + this.processes.splice(sourceIndex, 1); this.scheduler.handleInterrupt(this, source, interrupt); } } diff --git a/src/Scheduler.js b/src/Scheduler.js index 3bca870..fbe80e2 100644 --- a/src/Scheduler.js +++ b/src/Scheduler.js @@ -1,6 +1,7 @@ const Queue = require('./Queue'); const { QueueType, + SchedulerInterrupt, PRIORITY_LEVELS, } = require('./constants/index'); @@ -24,21 +25,57 @@ class Scheduler { // On every iteration of the scheduler, if the blocking queue is not empty, blocking work // should be done. Once the blocking work has been done, perform some CPU work in the same iteration. run() { + const time = Date.now(); + const timeSlice = time - this.clock; + this.clock = time; + if (!this.blockingQueue.isEmpty()) { + this.blockingQueue.doBlockingWork(timeSlice); + } + + for (let i=0; i queue.isEmpty()) && this.blockingQueue.isEmpty(); } addNewProcess(process) { - + this.runningQueues[0].enqueue(process); } // The scheduler's interrupt handler that receives a queue, a process, and an interrupt string constant // Should handle PROCESS_BLOCKED, PROCESS_READY, and LOWER_PRIORITY interrupts. handleInterrupt(queue, process, interrupt) { - + switch(interrupt) { + case SchedulerInterrupt.PROCESS_BLOCKED: + this.blockingQueue.enqueue(process); + break; + case SchedulerInterrupt.PROCESS_READY: + this.addNewProcess(process); + break; + case SchedulerInterrupt.LOWER_PRIORITY: + if (queue.getQueueType() === QueueType.CPU_QUEUE) { + const priorityLevel = Math.min(PRIORITY_LEVELS-1, queue.getPriorityLevel()+1); + this.runningQueues[priorityLevel].enqueue(process); + } else { + this.blockingQueue.enqueue(process); + } + break; + default: + break; + } } // Private function used for testing; DO NOT MODIFY From 83c596d429cc6ffceac520a11d61f24f13f67fc3 Mon Sep 17 00:00:00 2001 From: Andrew Kolumbic Date: Thu, 23 Aug 2018 13:43:22 -0700 Subject: [PATCH 5/5] added missing while loop that corrects previous issue --- src/Scheduler.js | 36 +++++++++++++++++++----------------- 1 file changed, 19 insertions(+), 17 deletions(-) diff --git a/src/Scheduler.js b/src/Scheduler.js index fbe80e2..afa0aa2 100644 --- a/src/Scheduler.js +++ b/src/Scheduler.js @@ -25,26 +25,28 @@ class Scheduler { // On every iteration of the scheduler, if the blocking queue is not empty, blocking work // should be done. Once the blocking work has been done, perform some CPU work in the same iteration. run() { - const time = Date.now(); - const timeSlice = time - this.clock; - this.clock = time; - - if (!this.blockingQueue.isEmpty()) { - this.blockingQueue.doBlockingWork(timeSlice); - } - - for (let i=0; i