// File: /workspace/github_cpp_makefile_star2_O1/QFSW[P]MIPS1-Simulator/src/Instructions.cpp
// Function: Clarkitechture::MIPS::BinaryDecoder::decodeIInstruction(unsigned int)
IInstruction* BinaryDecoder::decodeIInstruction(uint32_t bin)
{
	byte opcode = 0b111111 & (bin >> (32 - 6));
	byte rs = 0b11111 & (bin >> (32 - (6 + 5)));
	byte rt = 0b11111 & (bin >> (32 - (6 + 5 + 5)));
	uint16_t constant = 0xFFFF & bin;

	switch (opcode)
	{
	case 0b001000: return new ADDIInstr(rs, rt, constant);
    case 0b001001: return new ADDIUInstr(rs, rt, constant);
	case 0b001100: return new ANDIInstr(rs, rt, constant);
    case 0b001101: return new ORIInstr(rs, rt, constant);
    case 0b001110: return new XORIInstr(rs, rt, constant);
    case 0b001010: return new SLTIInstr(rs, rt, constant);
    case 0b001011: return new SLTIUInstr(rs, rt, constant);
    case 0b001111: return new LUIInstr(rs, rt, constant);
    case 0b100011: return new LWInstr(rs, rt, constant);
    case 0b100000: return new LBInstr(rs, rt, constant);
    case 0b100100: return new LBUInstr(rs, rt, constant);
    case 0b100001: return new LHInstr(rs, rt, constant);
    case 0b100101: return new LHUInstr(rs, rt, constant);
    case 0b101011: return new SWInstr(rs, rt, constant);
    case 0b101000: return new SBInstr(rs, rt, constant);
    case 0b101001: return new SHInstr(rs, rt, constant);
    case 0b000100: return new BEQInstr(rs, rt, constant);
    case 0b000111: return new BGTZInstr(rs, rt, constant);
    case 0b000110: return new BLEZInstr(rs, rt, constant);
    case 0b000101: return new BNEInstr(rs, rt, constant);
    case 0b100010: return new LWLInstr(rs, rt, constant);
    case 0b100110: return new LWRInstr(rs, rt, constant);
    case 0b000001: return decodeBranchInstruction(bin);
    default:
		throw BadInstructionDecode(bin, "invalid or unsupported opcode - " + toBinStr(opcode));
	}
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %rbx
subq $0x48, %rsp
movl %edi, %ebx
movl %edi, %r15d
shrl $0x1a, %r15d
leal -0x1(%r15), %eax
cmpl $0x2a, %eax
ja 0x96f0
movl %ebx, %r14d
shrl $0x15, %r14d
andb $0x1f, %r14b
movl %ebx, %ebp
shrl $0x10, %ebp
andb $0x1f, %bpl
leaq 0x340b(%rip), %rcx      # 0xc7f4
movslq (%rcx,%rax,4), %rax
addq %rcx, %rax
jmpq *%rax
movl %ebx, %edi
addq $0x48, %rsp
popq %rbx
popq %r14
popq %r15
popq %rbp
jmp 0x97a8
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7aa0(%rip), %rcx      # 0x10ec0
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7d1e(%rip), %rcx      # 0x11160
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x79ec(%rip), %rcx      # 0x10e50
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7bc2(%rip), %rcx      # 0x11048
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7ac0(%rip), %rcx      # 0x10f68
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x79be(%rip), %rcx      # 0x10e88
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x792c(%rip), %rcx      # 0x10e18
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7a22(%rip), %rcx      # 0x10f30
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7aa8(%rip), %rcx      # 0x10fd8
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7b2e(%rip), %rcx      # 0x11080
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7c24(%rip), %rcx      # 0x11198
jmp 0x96de
movl $0x18, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7d5a(%rip), %rcx      # 0x112f0
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7b00(%rip), %rcx      # 0x110b8
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x79c6(%rip), %rcx      # 0x10fa0
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7a14(%rip), %rcx      # 0x11010
jmp 0x96de
movl $0x18, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7bb2(%rip), %rcx      # 0x111d0
jmp 0x96de
movl $0x18, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7c68(%rip), %rcx      # 0x112a8
jmp 0x96de
movl $0x18, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7d66(%rip), %rcx      # 0x113c8
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7877(%rip), %rcx      # 0x10ef8
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7740(%rip), %rcx      # 0x10de0
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7a31(%rip), %rcx      # 0x110f0
jmp 0x96de
movl $0x10, %edi
callq 0x6200
movb %r14b, 0x8(%rax)
movb %bpl, 0x9(%rax)
movw %bx, 0xa(%rax)
leaq 0x7a4a(%rip), %rcx      # 0x11128
addq $0x10, %rcx
movq %rcx, (%rax)
addq $0x48, %rsp
popq %rbx
popq %r14
popq %r15
popq %rbp
retq
movl $0x50, %edi
callq 0x6100
movq %rax, %r14
leaq 0x8(%rsp), %rdi
movl %r15d, %esi
callq 0x9a01
leaq 0x3232(%rip), %rsi      # 0xc943
leaq 0x28(%rsp), %rdi
leaq 0x8(%rsp), %rdx
callq 0x9991
movb $0x1, %bpl
leaq 0x28(%rsp), %rdx
movq %r14, %rdi
movl %ebx, %esi
callq 0x6b82
xorl %ebp, %ebp
leaq 0x7645(%rip), %rsi      # 0x10d80
leaq -0x203e(%rip), %rdx     # 0x7704
movq %r14, %rdi
callq 0x6380
movq %rax, %rbx
leaq 0x38(%rsp), %rax
movq -0x10(%rax), %rdi
cmpq %rax, %rdi
je 0x9770
movq 0x38(%rsp), %rsi
incq %rsi
callq 0x6210
jmp 0x9770
movq %rax, %rbx
movb $0x1, %bpl
leaq 0x18(%rsp), %rax
movq -0x10(%rax), %rdi
cmpq %rax, %rdi
je 0x9793
movq 0x18(%rsp), %rsi
incq %rsi
callq 0x6210
jmp 0x9793
movq %rax, %rbx
movb $0x1, %bpl
testb %bpl, %bpl
je 0x97a0
movq %r14, %rdi
callq 0x6190
movq %rbx, %rdi
callq 0x63a0