Mon, 04 Oct, 2022

    
        Since others may have been confused by this element of today's class, I am
        sending my answer to the student's question to the entire class.  I apologize
        for the length of my answer.  I did not have enough time to write a short
        answer. 

        A student writes:
    
    
        > Hello Dr. Patt,
        >
        > I believe today in lecture you mentioned a process interrupting another and
        > being switched to if the interrupting process has higher priority. I am a
        > bit confused because I thought that processes could not directly interrupt
        > other processes, only ask the kernel to send a signal for the receiving
        > process to pick up when it next happens to enter supervisor mode.
    
    
        First, I apologize for not being completely clear.  You are correct, it is
        usually the operating system that saves the context of the process that is
        being interrupted and loads the context of the process that is about to take
        over.  In fact, the O/S can be in an idle state, waiting to be asked to do
        just that, and when it gets a signal to do it, wakes up and does it!
        
        But in the case of the LC-3b (and LC-3 back in EE306), we can actually do it
        in hardware by adding states to the microarchitecture's state machine
        that will be executed if in fact we need to interrupt one process in order
        to give the machine to another process.  In fact, your job in Lab 4 is to
        provide the additional states, additions to the data path and additional
        control signals to do it in the microarchitecture.
    
    
        > Especially as the interrupting process is not running, I'm not sure how it
        > would be able to interrupt a running process. Do I have my facts muddled
        > somewhere?
    
    
        Yes, the interrupting process is not running, but it does have logic structures
        associated with it that enables this to happen. 

        In class I mentioned what I consider the three most important items associated
        with a non-running process A that can be used to kick out the lower priority
        process B and start processing process A.  All three are discussed in detail
        in Chapter 9 of the EE306 textbook:

        1. A bit (I call it IE for "interrupt enable") which gives process A the
        right to attempt to access the machine if it thinks its priority is higher
        than the priority of process B which is currently running.

        2. A bit (I call it the ready bit R) which indicates that process A wants
        to access the machine.  Both IE and R are inputs to an AND gate.  If the output
        of the AND gate is 1, this process wants to interrupt NOW!.

        3. A vector (I call it an "interrupt vector") associated with each process
        which provides needed information for process A to get control of the computer.
        Usually, that interrupt vector is used by the operating system to give control
        of the computer to process A.  But in our simpler example with the LC-3 from
        EE306 and the LC-3b of EE460N, that vector can directly (as we shall see) give
        control of the computer to process A.

        Now, then, while process B is executing and process A wants to kick out
        process B and start executing, we have some logic going on.  Most importantly
        is the comparison of the priority of process A and the priority of process B.
        If the IE bit and R bit of process A are both 1 and the priority of process A
        is greater than the priority of process B, a logic signal will be produced
        that the context of B should be saved, and the context of A should be started.
        As I said this is usually handled by the operating system.  But we can handle
        it in our state machine with a microbranch that will take an alternate path
        if IE and R are both 1 and the priority of process A is greater than the
        priority of process B.  New states in the state machine (generated by YOU!)
        will push on the stack the context associated with process B (in our case,
        the PC and PSR of process b) and will load the PSR and PC with those of
        process A.  Once the PC of process A is loaded, process A has control of the
        computer and can start processing.

        We accomplished the last step of loading PC by using our interrupt vector
        as the address in the interrupt vector table that contains the starting address
        of the code for process A.
    
    
        > I apologize if this is not the best channel to ask on. Thanks for reading.
    
    
        Any channel is the best channel if you are comfortable with it and you think
        it can help you better understand.
    
    
        > Regards,
        > <<name withheld to protect the student who provided me with the incentive
        > to try to explain it again>>
    
    
        Thanks for the question.  If it is still not clear, feel free to send me
        another email, ask my TAs, or ask me in class on Monday.  It is an important
        concept.  Since 460N is a computer architecture course, I took the luxury of
        solving the problem with additional hardware in the microarchitecture, although
        yes, most computers would have the O/S deal with it.

        As I have said many times, most things can be done in hardware or in software,
        depending on how we decide to deal with the tradeoffs.

        Enjoy the rest of the week and good luck on the midterm next week.