gpcas_isa/
instruction.rs

1// Filename: instruction.rs
2// Version:	 0.8
3// Date:	 18-11-2021 (DD-MM-YYYY)
4// Library:  gpcas_isa
5//
6// Copyright (c) 2021 Kai Rese
7// This program is free software: you can redistribute it and/or modify
8// it under the terms of the GNU Lesser General Public License as
9// published by the Free Software Foundation, either version 3 of the
10// License, or (at your option) any later version.
11//
12// This program is distributed in the hope that it will be useful,
13// but WITHOUT ANY WARRANTY; without even the implied warranty of
14// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15// GNU Lesser General Public License for more details.
16//
17// You should have received a copy of the GNU Lesser General Public
18// License along with this program. If not, see
19// <https://www.gnu.org/licenses/>.
20
21//! Contains data structs and enums used by the emulator to send instructions to the simulator.
22
23/// The maximum number of register inputs that is needed by any ISA.
24pub const MAX_INPUTS: usize = 4;
25/// This flag gets set in the register indices. It indicates that the index is for a vector
26/// register and therefore might be using a separate register set.
27pub const IS_VECTOR_REGISTER: u8 = 0x20;
28
29/// An emulated instruction from the program of the simulation.
30///
31/// The emulator frontend sends one `Instruction` for each instruction it emulates. The simulator
32/// backend then uses it to do timing simulation.
33#[derive(Debug, Default, Clone)]
34pub struct Instruction {
35    /// The address of the instruction.
36    pub address: usize,
37    /// Contains the address of the memory operand, if it has one.
38    pub memory_address: usize,
39    /// The target address of the branch, provided the instruction is one.
40    pub branch_address: usize,
41    /// An ID for the instruction class, see `instruction_type` in the gpcas_base crate. Determines
42    /// execution time in the ALU, as well as possible restrictions for execution pipe choice in the
43    /// model.
44    pub instr_type: u16,
45    /// Contains the size of the memory operand in bytes.
46    pub memory_operand_size: u16,
47    /// Bitflags for different properties of the instruction, see [`instruction_flags`].
48    pub flags: u16,
49    /// The register indices of the inputs. The full input count may not be needed by all ISAs.
50    ///
51    /// Registers used as input operands are saved after ones for memory operand calculation.
52    pub inputs: [u8; MAX_INPUTS],
53    /// How many register inputs the instruction uses in total.
54    pub input_register_count: u8,
55    /// How many register inputs are used for memory operand calculation.
56    pub memory_register_count: u8,
57    /// The register index of the output if the instruction has one.
58    pub output: u8,
59    /// Size of the instruction in bytes.
60    pub size: u8,
61}
62
63/// Contains constants for control information for the cpu simulation.
64///
65/// This module contains the flag constants used in [`Instruction::flags`].
66pub mod instruction_flags {
67    /// The branch is taken.
68    ///
69    /// This should only be checked if the branch type is [`BR_TYPE_CONDITIONAL`].
70    pub const BR_TAKEN: u16 = 0x0001;
71    /// The branch is a return from a call.
72    ///
73    /// This should only be checked if the branch type is [`BR_TYPE_CALL`].
74    pub const BR_RETURN: u16 = BR_TAKEN;
75    /// The branch uses registers or a memory operand to determine the target address.
76    ///
77    /// If this is set, the target address might get predicted, but not resolved in the front end of
78    /// the front end of the model pipeline.
79    pub const BR_INDIRECT: u16 = 0x0002;
80    /// The instruction is no branch of any form.
81    pub const BR_TYPE_NONE: u16 = 0x0000;
82    /// The instruction is a unconditional jump.
83    pub const BR_TYPE_JUMP: u16 = 0x0004;
84    /// The instruction is a conditional branch.
85    pub const BR_TYPE_CONDITIONAL: u16 = 0x0008;
86    /// The instruction is either a call or a return instruction.
87    pub const BR_TYPE_CALL: u16 = 0x000C;
88    /// The bitmask for the branch type. Use this to check the type.
89    pub const BR_TYPE_MASK: u16 = 0x000C;
90
91    /// The instruction has a memory input.
92    pub const MEM_IN: u16 = 0x0010;
93    /// The instruction has a memory output.
94    pub const MEM_OUT: u16 = 0x0020;
95    /// The instruction has a register output.
96    pub const REG_OUT: u16 = 0x0040;
97    /// The memory operand is a vector.
98    ///
99    /// This is used for special vector treatment in case it is necessary.
100    pub const MEM_VECTOR: u16 = 0x0080;
101
102    /// The instruction is a micro-operation of a more complex instruction and has another
103    /// micro-operation of the same instruction following after it.
104    pub const HAS_FOLLOW_UP: u16 = 0x0100;
105    /// The instruction switches the execution context, for example when executing a system call.
106    /// This can have different effects on the hardware which could be simulated as flushing the L1
107    /// caches, for example.
108    pub const CONTEXT_CHANGE: u16 = 0x0200;
109    /// The simulator should terminate after this instruction.
110    ///
111    /// Currently there is no difference between a normal exit, a panic or other exceptions.
112    pub const TERMINATE: u16 = 0x8000;
113}