diff options
Diffstat (limited to 'pysc-v/InstructionSets/RV32I.py')
-rw-r--r-- | pysc-v/InstructionSets/RV32I.py | 461 |
1 files changed, 0 insertions, 461 deletions
diff --git a/pysc-v/InstructionSets/RV32I.py b/pysc-v/InstructionSets/RV32I.py deleted file mode 100644 index f2929f3..0000000 --- a/pysc-v/InstructionSets/RV32I.py +++ /dev/null @@ -1,461 +0,0 @@ -from .instructions import Instruction, InstructionSet -from ctypes import c_uint32 - -RV32I = InstructionSet() - -class R(Instruction): - funct3 = None - funct7 = None - opcode = None - def __init__(self, rd, rs1, rs2): - self.rd = rd - self.rs1 = rs1 - self.rs2 = rs2 - - def compile(self): - # TODO: ensure sizes and convert register names to number... - return c_uint32( - (self.funct7 << 25) +\ - (self.rs2 << 20) +\ - (self.rs1 << 15) +\ - (self.funct3 << 12) +\ - (self.rd << 7) +\ - self.opcode - ) - -class I(Instruction): - funct3 = None - opcode = None - - def __init__(self, rd, rs, imm): - self.rd = rd - self.rs = rs - self.imm = imm - - def compile(self): - return c_uint32( - (self.imm << 20) +\ - (self.rs << 15) +\ - (self.funct3 << 12) +\ - (self.rd << 7) +\ - self.opcode - ) - -class S(Instruction): - funct3 = None - opcode = None - - def __init__(self, rs1, rs2, imm): - self.rs1 = rs1 - self.rs2 = rs2 - self.imm = imm - - def compile(self): - imm_0_4 = self.imm & 0x1F - imm_5_11 = (self.imm & 0xFE0)>>5 - return c_uint32( - (imm_5_11 << 25) +\ - (self.rs1 << 20) +\ - (self.rs2 << 15) +\ - (self.funct3 << 12) +\ - (imm_0_4 << 7) +\ - self.opcode - ) - -class B(Instruction): - funct3 = None - opcode = None - - def __init__(self, rs1, rs2, imm): - self.rs1 = rs1 - self.rs2 = rs2 - self.imm = imm - - def compile(self): - # NOTE: The lowest bit of the imm is always 0 because instructions - # are at least 16 bits wide, so it's not used, that's why this - # instruction looks that weird - imm_12 = (self.imm & 0b1000000000000)>>12 - imm_11 = (self.imm & 0b0100000000000)>>11 - imm_5_10 = (self.imm & 0b0011111100000)>>5 - imm_1_4 = (self.imm & 0b0000000011110)>>1 - return c_uint32( - (imm_12 << 31) +\ - (imm_5_10 << 25) +\ - (self.rs2 << 20) +\ - (self.rs1 << 15) +\ - (self.funct3 << 12) +\ - (imm_1_4 << 8) +\ - (imm_11 << 7) +\ - self.opcode - ) - - -class U(Instruction): - opcode = None - def __init__(self, rd, imm): - self.rd = rd - self.imm = imm - - def compile(self): - # NOTE: U Type is for AUIPC and LUI that only use the high part of the - # immediate - imm_12_32 = (self.imm & 0xFFFFF000)>>12 - return c_uint32( - (imm_12_32 << 12) +\ - (self.rd << 7) +\ - self.opcode - ) - -class J(Instruction): - opcode = None - - def __init__(self, rd, imm): - self.rd = rd - self.imm = imm - - def compile(self): - # NOTE: Jumps are also weird - imm_20 = (self.imm & 0x100000)>>20 - imm_12_19 = (self.imm & 0x0FF000)>>12 - imm_11 = (self.imm & 0x000800)>>11 - imm_1_10 = (self.imm & 0x0007FE)>>1 - return c_uint32( - (imm_20 << 31) +\ - (imm_1_10 << 21) +\ - (imm_11 << 20) +\ - (imm_12_19 << 12) +\ - (self.rd << 7) +\ - self.opcode - ) - - - - -@RV32I.instruction -class lui(U): - name = "lui" - opcode = 0b0110111 - -@RV32I.instruction -class auipc(U): - name = "auipc" - opcode = 0b0010111 - -@RV32I.instruction -class jal(J): - name = "jal" - opcode = 0b1101111 - - def execute(self, pc): - # TODO - # - Save current pc in rd - # - Make pc from `imm` - # - Return new pc - return pc - -@RV32I.instruction -class jalr(I): - name = "jalr" - opcode = 0b1100111 - funct3 = 0b000 - -@RV32I.instruction -class beq(B): - name = "beq" - opcode = 0b1100011 - funct3 = 0b000 - -@RV32I.instruction -class bne(B): - name = "bne" - opcode = 0b1100011 - funct3 = 0b001 - -@RV32I.instruction -class blt(B): - name = "blt" - opcode = 0b1100011 - funct3 = 0b100 - -@RV32I.instruction -class bge(B): - name = "bge" - opcode = 0b1100011 - funct3 = 0b101 - -@RV32I.instruction -class bltu(B): - name = "bltu" - opcode = 0b1100011 - funct3 = 0b110 - -@RV32I.instruction -class bgeu(B): - name = "bgeu" - opcode = 0b1100011 - funct3 = 0b111 - -@RV32I.instruction -class lb(I): - name = "lb" - opcode = 0b0000011 - funct3 = 0b000 - -@RV32I.instruction -class lh(I): - name = "lh" - opcode = 0b0000011 - funct3 = 0b001 - -@RV32I.instruction -class lw(I): - name = "lw" - opcode = 0b0000011 - funct3 = 0b010 - -@RV32I.instruction -class lbu(I): - name = "lbu" - opcode = 0b0000011 - funct3 = 0b100 - -@RV32I.instruction -class lhu(I): - name = "lhu" - opcode = 0b0000011 - funct3 = 0b101 - - -@RV32I.instruction -class sb(S): - name = "sb" - opcode = 0b0100011 - funct3 = 0b000 - -@RV32I.instruction -class sh(S): - name = "sh" - opcode = 0b0100011 - funct3 = 0b001 - -@RV32I.instruction -class sw(S): - name = "sw" - opcode = 0b0100011 - funct3 = 0b010 - -@RV32I.instruction -class addi(I): - name = "addi" - opcode = 0b0010011 - funct3 = 0b000 - - def execute(self, pc): - # TODO - return pc + self.size - -@RV32I.instruction -class slti(I): - name = "slti" - opcode = 0b0010011 - funct3 = 0b010 - -@RV32I.instruction -class sltiu(I): - name = "sltiu" - opcode = 0b0010011 - funct3 = 0b011 - -@RV32I.instruction -class xori(I): - name = "xori" - opcode = 0b0010011 - funct3 = 0b100 - -@RV32I.instruction -class ori(I): - name = "ori" - opcode = 0b0010011 - funct3 = 0b110 - -@RV32I.instruction -class andi(I): - name = "andi" - opcode = 0b0010011 - funct3 = 0b111 - - -class ShiftImm(I): - # NOTE: This is an special type used for shifting operations because they - # have 7 bits left after the maximum shift (5bits -> 32 rotations) - # they can apply. - # In RV64I they can indicate rotation with 1 bit more (64 rotations) so - # they use a funct6 instead. - funct7 = None - funct3 = None - opcode = None - - def __init__(self, rd, rs, imm): - self.rd = rd - self.rs = rs - self.imm = imm - - def compile(self): - return c_uint32( - (self.funct7 << 25) +\ - (self.imm << 20) +\ - (self.rs << 15) +\ - (self.funct3 << 12) +\ - (self.rd << 7) +\ - self.opcode - ) - -@RV32I.instruction -class slli(ShiftImm): - name = "slli" - opcode = 0b0010011 - funct3 = 0b001 - funct7 = 0b0000000 - -@RV32I.instruction -class srli(ShiftImm): - name = "srli" - opcode = 0b0010011 - funct3 = 0b101 - funct7 = 0b0000000 - -@RV32I.instruction -class srai(ShiftImm): - name = "srai" - opcode = 0b0010011 - funct3 = 0b101 - funct7 = 0b0100000 - - -@RV32I.instruction -class add(R): - name = "add" - opcode = 0b0110011 - funct3 = 0b000 - funct7 = 0b0000000 - - def execute(self, pc): - # TODO - return pc + self.size - -@RV32I.instruction -class sub(R): - name = "sub" - opcode = 0b0110011 - funct3 = 0b000 - funct7 = 0b0100000 - -@RV32I.instruction -class sll(R): - name = "sll" - opcode = 0b0110011 - funct3 = 0b001 - funct7 = 0b0000000 - -@RV32I.instruction -class slt(R): - name = "slt" - opcode = 0b0110011 - funct3 = 0b010 - funct7 = 0b0000000 - -@RV32I.instruction -class sltu(R): - name = "sltu" - opcode = 0b0110011 - funct3 = 0b011 - funct7 = 0b0000000 - -@RV32I.instruction -class xor(R): - name = "xor" - opcode = 0b0110011 - funct3 = 0b100 - funct7 = 0b0000000 - -@RV32I.instruction -class srl(R): - name = "srl" - opcode = 0b0110011 - funct3 = 0b101 - funct7 = 0b0000000 - -@RV32I.instruction -class sra(R): - name = "sra" - opcode = 0b0110011 - funct3 = 0b101 - funct7 = 0b0100000 - -@RV32I.instruction -class _or(R): - name = "or" - opcode = 0b0110011 - funct3 = 0b110 - funct7 = 0b0000000 - -@RV32I.instruction -class _and(R): - name = "and" - opcode = 0b0110011 - funct3 = 0b111 - funct7 = 0b0000000 - -@RV32I.instruction -class ecall(I): - name = "ecall" - opcode = 0b1110011 - funct3 = 0b000 - - def __init__(self): - # NOTE: ecall is a I-type instruction but doesn't get any arg and sets - # every field to 0 - self.rd = 0b00000 - self.rs = 0b00000 - self.imm = 0b000000000000 - - -@RV32I.instruction -class ebreak(I): - name = "ebreak" - opcode = 0b1110011 - funct3 = 0b000 - - def __init__(self): - # NOTE: ebreak is a I-type instruction but doesn't get any arg and pre- - # -sets every field to a fixed value - self.rd = 0b00000 - self.rs = 0b00000 - self.imm = 0b000000000001 - - - - - - - - - - - - - - - - -@RV32I.pseudoinstruction -class j(J): - name = "j" - def __new__(cls, imm): - return jal("x0", imm) - - -if __name__ == "__main__": - print(RV32I) - print(RV32I.instructions) |