The StaticInst provides all static information and methods for a binary instruction.
It holds the following information/methods:
- Flags to tell what kind of instruction it is (integer, floating point, branch, memory barrier, etc.)
- The op class of the instruction
- The number of source and destination registers
- The number of integer and FP registers used
- Method to decode a binary instruction into a StaticInst
- Virtual function execute(), which defines how the specific architectural actions taken for an instruction (e.g. read r1, r2, add them and store in r3.)
- Virtual functions to handle starting and completing memory operations
- Virtual functions to execute the address calculation and memory access separately for models that split memory operations into two operations
- Method to disassemble the instruction, printing it out in a human readable format. (e.g.
addq r1 r2 r3)
It does not have dynamic information, such as the PC of the instruction or the values of the source registers or the result. This allows a 1 to 1 mapping of StaticInst to unique binary machine instructions. We take advantage of this fact by caching the mapping of a binary instruction to a StaticInst in a hash_map, allowing us to decode a binary instruction only once, and directly using the StaticInst the rest of the time.
Each ISA instruction derives from StaticInst and implements its own constructor, the execute() function, and, if it is a memory instruction, the memory access functions. See ISA_description_system for details about how these ISA instructions are specified.
The DynInst is used to hold dynamic information about instructions. This is necessary for more detailed models or out-of-order models, both of which may need extra information beyond the StaticInst in order to correctly execute instructions.
Some of the dynamic information that it stores includes:
- The PC of the instruction
- The renamed register indices of the source and destination registers
- The predicted next-PC
- The instruction result
- The thread number of the instruction
- The CPU the instruction is executing on
- Whether or not the instruction is squashed
Additionally the DynInst provides the ExecContext interface. When ISA instructions are executed, the DynInst is passed in as the ExecContext, handling all accesses of the ISA to CPU state.
Detailed CPU models can derive from DynInst and create their own specific DynInst subclasses that implement any additional state or functions that might be needed. See src/cpu/o3/alpha/dyn_inst.hh for an example of this.
The ThreadState class is used to hold thread state that is common across CPU models, such as the thread ID, thread status, kernel statistics, memory port pointers, and some statistics of number of instructions completed. Each CPU model can derive from ThreadState and build upon it, adding in thread state that is deemed appropriate. An example of this is SimpleThread, where all of the thread's architectural state has been added in. However, it is not necessary (or even feasible in some cases) for all of the thread's state to be centrally located in a ThreadState derived class. The DetailedCPU keeps register values and rename maps in its own classes outside of ThreadState. ThreadState is only used to provide a more convenient way to centrally locate some state, and provide sharing across CPU models.