// File: QFSW[P]MIPS1-Simulator/src/main.cpp
// Function: main
int main(int argc, const char * argv[])
{
    std::string fileName;
    Simulator sim;
        
    try
    {
        if (argc <= 1) { throw BadBinaryIO("please add the file path to the binary code to simulate as the first argument."); }
        else { fileName = argv[1]; }

        std::cerr << "loading binary file '" << fileName << "'..." << std::endl;
        sim.loadMachineCode(fileName);
        std::cerr << "load success\nsimulating CPU...\n";
        std::cerr << "=====================" << std::endl;
        sim.simulate();
        std::cerr << "\n=====================" << std::endl;
        std::cerr << "simulation success\n";
        std::exit(sim.getExitCode());
    }
    catch (const MIPSException &e)
    {
        std::cerr << "\n\nsimulation failed\n" << e.what() << std::endl;
        std::exit(e.exitCode());
    }
    catch (...)
    {
        std::cerr << "\n\nan unknown internal error occurred" << std::endl;
        std::exit(-20);
    }
    return 0;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x200, %rsp            # imm = 0x200
movl $0x0, -0x4(%rbp)
movl %edi, -0x8(%rbp)
movq %rsi, -0x10(%rbp)
leaq -0x30(%rbp), %rdi
callq 0x63c0
leaq -0x138(%rbp), %rdi
callq 0x132f0
jmp 0x12f00
cmpl $0x1, -0x8(%rbp)
jg 0x12ffd
movb $0x1, -0x16a(%rbp)
movl $0x48, %edi
callq 0x6140
movq %rax, -0x1a8(%rbp)
leaq -0x169(%rbp), %rdi
movq %rdi, -0x1a0(%rbp)
callq 0x64c0
movq -0x1a0(%rbp), %rdx
leaq 0x2149(%rip), %rsi      # 0x1508c
leaq -0x168(%rbp), %rdi
callq 0x8b50
jmp 0x12f51
movq -0x1a8(%rbp), %rdi
leaq -0x168(%rbp), %rsi
callq 0x6d30
jmp 0x12f66
movq -0x1a8(%rbp), %rdi
movb $0x0, -0x16a(%rbp)
leaq 0x8f75(%rip), %rsi      # 0x1bef0
leaq -0xb6d2(%rip), %rdx     # 0x78b0
callq 0x6470
jmp 0x132e4
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x140(%rbp)
movl %eax, -0x144(%rbp)
jmp 0x132c7
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x140(%rbp)
movl %eax, -0x144(%rbp)
jmp 0x12fd5
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x140(%rbp)
movl %eax, -0x144(%rbp)
leaq -0x168(%rbp), %rdi
callq 0x6190
leaq -0x169(%rbp), %rdi
callq 0x62e0
testb $0x1, -0x16a(%rbp)
jne 0x12fec
jmp 0x12ff8
movq -0x1a8(%rbp), %rdi
callq 0x61f0
jmp 0x1319c
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rsi
leaq -0x30(%rbp), %rdi
callq 0x63b0
jmp 0x13010
jmp 0x13029
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x140(%rbp)
movl %eax, -0x144(%rbp)
jmp 0x1319c
movq 0x9fc0(%rip), %rdi      # 0x1cff0
leaq 0x20a4(%rip), %rsi      # 0x150db
callq 0x6290
movq %rax, -0x1b0(%rbp)
jmp 0x13045
movq -0x1b0(%rbp), %rdi
leaq -0x30(%rbp), %rsi
callq 0x6270
movq %rax, -0x1b8(%rbp)
jmp 0x1305e
movq -0x1b8(%rbp), %rdi
leaq 0x2085(%rip), %rsi      # 0x150f1
callq 0x6290
movq %rax, -0x1c0(%rbp)
jmp 0x1307a
movq -0x1c0(%rbp), %rdi
movq 0x9f20(%rip), %rsi      # 0x1cfa8
callq 0x62c0
jmp 0x1308f
leaq -0x190(%rbp), %rdi
leaq -0x30(%rbp), %rsi
callq 0x6120
jmp 0x130a1
leaq -0x138(%rbp), %rdi
leaq -0x190(%rbp), %rsi
callq 0x10c70
jmp 0x130b6
leaq -0x190(%rbp), %rdi
callq 0x6190
movq 0x9f27(%rip), %rdi      # 0x1cff0
leaq 0x2026(%rip), %rsi      # 0x150f6
callq 0x6290
jmp 0x130d7
movq 0x9f12(%rip), %rdi      # 0x1cff0
leaq 0x2032(%rip), %rsi      # 0x15117
callq 0x6290
movq %rax, -0x1c8(%rbp)
jmp 0x130f3
movq -0x1c8(%rbp), %rdi
movq 0x9ea7(%rip), %rsi      # 0x1cfa8
callq 0x62c0
jmp 0x13108
leaq -0x138(%rbp), %rdi
callq 0x116e0
jmp 0x13116
movq 0x9ed3(%rip), %rdi      # 0x1cff0
leaq 0x1ff2(%rip), %rsi      # 0x15116
callq 0x6290
movq %rax, -0x1d0(%rbp)
jmp 0x13132
movq -0x1d0(%rbp), %rdi
movq 0x9e68(%rip), %rsi      # 0x1cfa8
callq 0x62c0
jmp 0x13147
movq 0x9ea2(%rip), %rdi      # 0x1cff0
leaq 0x1fd8(%rip), %rsi      # 0x1512d
callq 0x6290
jmp 0x1315c
leaq -0x138(%rbp), %rdi
callq 0x11720
movb %al, -0x1d1(%rbp)
jmp 0x13170
movb -0x1d1(%rbp), %al
movzbl %al, %edi
callq 0x6340
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x140(%rbp)
movl %eax, -0x144(%rbp)
leaq -0x190(%rbp), %rdi
callq 0x6190
movl -0x144(%rbp), %eax
movl $0x2, %ecx
cmpl %ecx, %eax
jne 0x1323e
movq -0x140(%rbp), %rdi
callq 0x60f0
movq %rax, -0x198(%rbp)
movq 0x9e27(%rip), %rdi      # 0x1cff0
leaq 0x1f96(%rip), %rsi      # 0x15166
callq 0x6290
movq %rax, -0x1e0(%rbp)
jmp 0x131de
movq -0x198(%rbp), %rdi
movq (%rdi), %rax
movq 0x10(%rax), %rax
callq *%rax
movq -0x1e0(%rbp), %rdi
movq %rax, %rsi
callq 0x6290
movq %rax, -0x1e8(%rbp)
jmp 0x13206
movq -0x1e8(%rbp), %rdi
movq 0x9d94(%rip), %rsi      # 0x1cfa8
callq 0x62c0
jmp 0x1321b
movq -0x198(%rbp), %rdi
movq (%rdi), %rax
movq 0x18(%rax), %rax
callq *%rax
movl %eax, -0x1ec(%rbp)
jmp 0x13233
movl -0x1ec(%rbp), %edi
callq 0x6340
movq -0x140(%rbp), %rdi
callq 0x60f0
movq 0x9d9f(%rip), %rdi      # 0x1cff0
leaq 0x1ee9(%rip), %rsi      # 0x15141
callq 0x6290
movq %rax, -0x1f8(%rbp)
jmp 0x13266
movq -0x1f8(%rbp), %rdi
movq 0x9d34(%rip), %rsi      # 0x1cfa8
callq 0x62c0
jmp 0x1327b
movl $0xffffffec, %edi       # imm = 0xFFFFFFEC
callq 0x6340
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x140(%rbp)
movl %eax, -0x144(%rbp)
callq 0x6460
jmp 0x1329e
jmp 0x132bb
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x140(%rbp)
movl %eax, -0x144(%rbp)
callq 0x6460
jmp 0x132b9
jmp 0x132bb
leaq -0x138(%rbp), %rdi
callq 0x13380
leaq -0x30(%rbp), %rdi
callq 0x6190
movq -0x140(%rbp), %rdi
callq 0x64b0
movq %rax, %rdi
callq 0xa6d0
nopw %cs:(%rax,%rax)
nop