+1 (315) 557-6473 

Operating System Programming Assignment Solution


Operating System Assignment

Assignment:

Write an operating system assignment, you will simulate the 5-state model as managed. You will also practice creating a new process and communicating with it. You will create two programs: The OS/CPU program to represent the execution and management of processes, and the I/O Bus program to represent the various I/O devices attached to the System bus that a process may try to access.

Operating System

The OS program will be the one that launches the entire project. It will take, on the command line, the name of the transcript file (see below). When launched, the OS program will create a new process, running the I/O bus program and performing any set-up that is needed. The two processes will communicate with each other through pipes. If you choose to use C or C++, then you are required to use the Linux system calls to fork the process and setup the pipes. Python and Java provide their own system independent methods. Timing will be important in this project. We will use “executing an instruction” as a tick in our clock. The detail of what it means to execute an instruction is in the “The OS” section below. After the execution of an instruction the clock moves by one, and the OS program will send a “tick” command to the I/O Bus program.

Solution:

OS Program:

package com.company; import java.io.*; import java.util.ArrayList; import java.util.LinkedList; public class OS { private static PipedInputStream IOBusInputStream; private static PipedOutputStream IOBusOutputStream; private static IOBus IOThread; private static int ticks = 0; private static ProcessState state = ProcessState.RUNNING; private static int waitingTicks = 0; private static boolean transcriptFinished = false; private static LinkedList processQueue = new LinkedList<>(); private static String currentProgram = null; private static ProcessControlBlock currentProgramControlBlock = null; private static int processCount = 0; public static void main(String[] args) { // write your code here PipedOutputStream IOOutputStream = null; PipedInputStream IOInputStream = null; try { IOOutputStream = new PipedOutputStream(); IOBusOutputStream = new PipedOutputStream(); IOInputStream = new PipedInputStream(IOBusOutputStream); IOBusInputStream = new PipedInputStream(IOOutputStream); } catch (IOException exception) { System.out.println("Critical error: Unable to create pipes."); System.exit(1); } IOThread = new IOBus(IOInputStream, IOOutputStream); IOThread.start(); if (args.length > 0) { try { BufferedReader transcriptReader = new BufferedReader(new FileReader(args[0])); BufferedReader processReader = null; String transcriptCommand; String programCommand; while(true){ //Check if a program is running, if it's not run one or exit if there's nothing else to run. if(currentProgram == null){ if(!processQueue.isEmpty()){ currentProgram = processQueue.removeFirst(); processReader = new BufferedReader(new FileReader(currentProgram)); currentProgramControlBlock = new ProcessControlBlock(ProcessState.NEW, processCount++, currentProgram, ticks); }else if(transcriptFinished && !IOThread.hasEvents()){ IOThread.stop(); IOBusInputStream.close(); IOOutputStream.close(); transcriptReader.close(); if(processReader!=null){ processReader.close(); } System.out.println("Completed."); return; //PROGRAM EXIT CONDITION } } //If a program is running... if(currentProgram != null){ if((programCommand = processReader.readLine()) != null){ switch (programCommand){ case "CPU": break; case "ERROR": currentProgramControlBlock.state = ProcessState.TERMINATED; //Program terminated break; default: System.out.println("Received " + programCommand + " at tick: " + ticks); IOBusOutputStream.write(Integer.parseInt(programCommand.split(" ")[1])); } } if(programCommand == null || currentProgramControlBlock.state == ProcessState.TERMINATED){ // Program deletion logic currentProgram = null; System.out.println("Process exited and deleted: " + currentProgramControlBlock + "tickDeleted = " + ticks + ", reason = '" + ((programCommand == null)?"Program ended": "Error") + "'"); } } //Do a tick. ticks++; IOBusOutputStream.write(IOBus.IOCodes.TICK.ordinal()); System.out.println("Tick: " + ticks); //Check for IOBus events while(IOBusInputStream.available() != 0){ int data = IOBusInputStream.read(); switch(IOBus.IOCodes.values()[data]){ case EVENT_1: System.out.println("Event 1 completed at time: " + ticks); break; case EVENT_2: System.out.println("Event 2 completed at time: " + ticks); break; case EVENT_3: System.out.println("Event 3 completed at time: " + ticks); break; } } //Process transcript. if(state == ProcessState.RUNNING){ if((transcriptCommand = transcriptReader.readLine()) != null){ if(transcriptCommand.startsWith("WAIT")){ state = ProcessState.WAITING; waitingTicks = Integer.parseInt(transcriptCommand.split(" ")[1]); } else { processQueue.add(transcriptCommand); } } else{ transcriptFinished = true; } } else { if(--waitingTicks <= 0){ state = ProcessState.RUNNING; } } } } catch (FileNotFoundException e) { System.out.println("Invalid path for transcript file. Not found."); return; } catch (IOException exception) { System.out.println("Error occurred while reading transcript file."); return; } } else{ System.out.println("Please enter some arguments."); return; } } }

I/O Bus Program:

package com.company; import java.io.IOException; import java.io.PipedInputStream; import java.io.PipedOutputStream; import java.util.ArrayList; public class IOBus extends Thread { private int ticks; private PipedInputStream inputStream; private PipedOutputStream outputStream; private ArrayList eventsList; enum IOCodes{ TICK, EVENT_1, EVENT_2, EVENT_3 } private class Event { private IOBus parent; private IOCodes eventType; private int remainingTicks; public Event(IOBus parent, IOCodes eventType, int remainingTicks) { this.parent = parent; this.eventType = eventType; this.remainingTicks = remainingTicks; } public void decrementTicks() throws IOException { if(--remainingTicks == 0){ parent.callEvent(eventType); } } } public IOBus(PipedInputStream inputStream, PipedOutputStream outputStream) { this.inputStream = inputStream; this.outputStream = outputStream; eventsList = new ArrayList<>(); ticks = 0; } private void callEvent(IOCodes code) throws IOException { this.outputStream.write(code.ordinal()); } public boolean hasEvents(){ return this.eventsList.size() > 0; } @Override public void run() { try{ do{ if(inputStream.available() != 0){ int data = inputStream.read(); switch(IOCodes.values()[data]){ case TICK: decrementAllEventCounters(); break; case EVENT_1: eventsList.add(new Event(this, IOCodes.EVENT_1, 3)); break; case EVENT_2: eventsList.add(new Event(this, IOCodes.EVENT_2, 5)); break; case EVENT_3: eventsList.add(new Event(this, IOCodes.EVENT_3, 7)); break; } } }while(true); } catch (Exception e){ e.printStackTrace(); System.out.println("Fatal IO error"); System.exit(1); } } private void decrementAllEventCounters() throws IOException { ArrayList finishedEvents = new ArrayList<>(); for (Event event: eventsList){ event.decrementTicks(); if(event.remainingTicks == 0){ finishedEvents.add(event); } } eventsList.removeAll(finishedEvents); } }