class MulDivInst(Enum): MUL = Enum.Auto() MULH = Enum.Auto() MULHU = Enum.Auto() MULHSU = Enum.Auto() DIV = Enum.Auto() DIVU = Enum.Auto() REM = Enum.Auto() REMU = Enum.Auto()
class ArithInst(Enum): ADD = Enum.Auto() SUB = Enum.Auto() SLT = Enum.Auto() SLTU = Enum.Auto() AND = Enum.Auto() OR = Enum.Auto() XOR = Enum.Auto()
class LoadInst(Enum): LB = Enum.Auto() LBU = Enum.Auto() LH = Enum.Auto() LHU = Enum.Auto() LW = Enum.Auto() LWU = Enum.Auto() LD = Enum.Auto()
class BranchInst(Enum): BEQ = Enum.Auto() BNE = Enum.Auto() BLT = Enum.Auto() BLTU = Enum.Auto() BGE = Enum.Auto() BGEU = Enum.Auto()
class RM(Enum): RNE = Enum.Auto() RTZ = Enum.Auto() RDN = Enum.Auto() RUP = Enum.Auto() RMM = Enum.Auto() DYN = Enum.Auto()
def _enum(isa: Enum) -> int: asm = {} dsm = {} layout = {} free = [] used = set() i_map = {} for inst in isa.enumerate(): val = inst._value_ if isinstance(val, int): used.add(val) i_map[inst] = val else: assert isinstance(val, EnumMeta.Auto) free.append(inst) c = 0 while free: inst = free.pop() while c in used: c += 1 used.add(c) i_map[inst] = c width = max(used).bit_length() for inst in isa.enumerate(): layout[inst] = (0, width) opcode = i_map[inst] asm[inst] = opcode dsm[opcode] = inst def assembler(inst): return asm[inst] def disassembler(opcode): return dsm[opcode] return assembler, disassembler, width, layout
def _enum(isa: Enum): encoding = {} decoding = {} layout = {} free = [] used = set() i_map = {} for inst in isa.enumerate(): if isinstance(inst.value, int): used.add(inst.value) i_map[inst] = inst.value else: assert isinstance(inst.value, EnumMeta.Auto) free.append(inst) c = 0 while free: inst = free.pop() while c in used: c += 1 used.add(c) i_map[inst] = c width = max(used).bit_length() for inst in isa.enumerate(): layout[inst] = (0, width, None) opcode = BitVector[width](i_map[inst]) encoding[inst] = opcode decoding[opcode] = inst def assembler(inst): return encoding[inst] def disassembler(bv): return decoding[bv] return assembler, disassembler, width, layout
class I2Inst(Enum): # Arith # ADDI - Traps ADDIU = Enum.Auto() # Logical ANDI = Enum.Auto() ORI = Enum.Auto() XORI = Enum.Auto() # Conditions SLTI = Enum.Auto() SLTIU = Enum.Auto()
class R2Inst(Enum): # Arith CLO = Enum.Auto() CLZ = Enum.Auto() SEB = Enum.Auto() SEH = Enum.Auto() #Logic WSBH = Enum.Auto() # Mul / Div DIV = Enum.Auto() DIVU = Enum.Auto() MADD = Enum.Auto() MADDU = Enum.Auto() MSUB = Enum.Auto() MSUBU = Enum.Auto() MULT = Enum.Auto() MULTU = Enum.Auto()
class RsInst(Enum): ROTR = Enum.Auto() SLL = Enum.Auto() SRA = Enum.Auto() SRL = Enum.Auto()
class RlmInst(Enum): EXT = Enum.Auto() INS = Enum.Auto()
class Opcode(Enum): ADD = Enum.Auto() SUB = Enum.Auto() AND = Enum.Auto() OR = Enum.Auto()
class FPMinMaxInst(Enum): MIN = Enum.Auto() MAX = Enum.Auto()
class FPCompareInst(Enum): EQ = Enum.Auto() LT = Enum.Auto() LE = Enum.Auto()
class FPFusedInst(Enum): FMA = Enum.Auto() FNMA = Enum.Auto() FMS = Enum.Auto() FNMS = Enum.Auto()
class Tag(Enum): tag_a = Enum.Auto() tag_i = 1
class FPOther(Enum): FSQRT = Enum.Auto() FCLASS = Enum.Auto()
class FPComputeInst(Enum): FADD = Enum.Auto() FSUB = Enum.Auto() FMUL = Enum.Auto() FDIV = Enum.Auto()
class TF(Enum): T = Enum.Auto() F = Enum.Auto()
class Opcode(Enum): NOR = Enum.Auto() JMP = Enum.Auto()
class ALUOp(Enum): AND = Enum.Auto() OR = Enum.Auto() XOR = Enum.Auto() ADD = Enum.Auto() MUL = Enum.Auto() DIV = Enum.Auto() # could definitely do this by resuing the other instructions # putting flags in the second output. I am lazy and it doesn't # matter LT = Enum.Auto() # Should put shifts in the own unit but whatever SHL = Enum.Auto() SHR = Enum.Auto() ROT = Enum.Auto() MOV = Enum.Auto() # Same for the bit twiddling ops CLO = Enum.Auto()
class BitInst(Enum): POPCNT = Enum.Auto() CNTLZ = Enum.Auto() CNTTZ = Enum.Auto()
class LOHI(Enum): LO = Enum.Auto() HI = Enum.Auto()
class ShiftInst(Enum): SLL = Enum.Auto() SRL = Enum.Auto() SRA = Enum.Auto()
class R3Inst(Enum): # Arith # ADD - Traps ADDU = Enum.Auto() # SUB - Traps SUBU = Enum.Auto() # Shifts ROTRV = Enum.Auto() SLLV = Enum.Auto() SRAV = Enum.Auto() SRLV = Enum.Auto() # Logic AND = Enum.Auto() NOR = Enum.Auto() OR = Enum.Auto() XOR = Enum.Auto() # Conditions MOVN = Enum.Auto() MOVZ = Enum.Auto() SLT = Enum.Auto() SLTU = Enum.Auto() # Mul / Div MUL = Enum.Auto()
class StoreInst(Enum): SB = Enum.Auto() SH = Enum.Auto() SW = Enum.Auto() SD = Enum.Auto()