// File: NishadSaraf[P]Championship-Simulator/src/ooo_cpu.cc
// Function: O3_CPU::reg_RAW_release(unsigned int)
void O3_CPU::reg_RAW_release(uint32_t rob_index)
{
    for (uint32_t i=0; i<ROB.SIZE; i++) {
        if (ROB.entry[rob_index].registers_instrs_depend_on_me[i]) {
            for (uint32_t j=0; j<NUM_INSTR_SOURCES; j++) {
                if (ROB.entry[rob_index].registers_index_depend_on_me[i][j]) {
                    ROB.entry[i].num_reg_dependent--;

                    if (ROB.entry[i].num_reg_dependent == 0) {
                        ROB.entry[i].reg_ready = 1;
                        if (ROB.entry[i].is_memory)
                            ROB.entry[i].scheduled = INFLIGHT;
                        else {
                            ROB.entry[i].scheduled = COMPLETED;

#ifdef SANITY_CHECK
                            if (RTE0[RTE0_tail] < ROB_SIZE)
                                assert(0);
#endif
                            // remember this rob_index in the Ready-To-Execute array 0
                            RTE0[RTE0_tail] = i;

                            DP (if (warmup_complete[cpu]) {
                            cout << "[RTE0] " << __func__ << " instr_id: " << ROB.entry[i].instr_id << " rob_index: " << i << " is added to RTE0";
                            cout << " head: " << RTE0_head << " tail: " << RTE0_tail << endl; }); 

                            RTE0_tail++;
                            if (RTE0_tail == ROB_SIZE)
                                RTE0_tail = 0;

                        }
                    }

                    DP (if (warmup_complete[cpu]) {
                    cout << "[ROB] " << __func__ << " instr_id: " << ROB.entry[rob_index].instr_id << " releases instr_id: ";
                    cout << ROB.entry[i].instr_id << " reg_index: " << +ROB.entry[i].source_registers[j] << " num_reg_dependent: " << ROB.entry[i].num_reg_dependent << " cycle: " << current_core_cycle[cpu] << endl; });
                }
            }
        }
    }
}

// Assembly:
subq $0x28, %rsp
movq %rdi, 0x20(%rsp)
movl %esi, 0x1c(%rsp)
movq 0x20(%rsp), %rax
movq %rax, 0x8(%rsp)
movl $0x0, 0x18(%rsp)
movq 0x8(%rsp), %rcx
movl 0x18(%rsp), %eax
cmpl 0x950(%rcx), %eax
jae 0x19eac
movq 0x8(%rsp), %rax
movq 0x9b8(%rax), %rax
movl 0x1c(%rsp), %ecx
imulq $0x758, %rcx, %rcx      # imm = 0x758
addq %rcx, %rax
movl 0x18(%rsp), %ecx
cmpb $0x0, 0x84(%rax,%rcx)
je 0x19e9a
movl $0x0, 0x14(%rsp)
cmpl $0x4, 0x14(%rsp)
jae 0x19e98
movq 0x8(%rsp), %rax
movq 0x9b8(%rax), %rax
movl 0x1c(%rsp), %ecx
imulq $0x758, %rcx, %rcx      # imm = 0x758
addq %rcx, %rax
addq $0x184, %rax            # imm = 0x184
movl 0x18(%rsp), %ecx
shlq $0x2, %rcx
addq %rcx, %rax
movl 0x14(%rsp), %ecx
cmpb $0x0, (%rax,%rcx)
je 0x19e86
movq 0x8(%rsp), %rax
movq 0x9b8(%rax), %rcx
movl 0x18(%rsp), %edx
imulq $0x758, %rdx, %rdx      # imm = 0x758
addq %rdx, %rcx
movl 0x74(%rcx), %edx
addl $-0x1, %edx
movl %edx, 0x74(%rcx)
movq 0x9b8(%rax), %rax
movl 0x18(%rsp), %ecx
imulq $0x758, %rcx, %rcx      # imm = 0x758
addq %rcx, %rax
cmpl $0x0, 0x74(%rax)
jne 0x19e84
movq 0x8(%rsp), %rax
movq 0x9b8(%rax), %rcx
movl 0x18(%rsp), %edx
imulq $0x758, %rdx, %rdx      # imm = 0x758
addq %rdx, %rcx
movb $0x1, 0x59(%rcx)
movq 0x9b8(%rax), %rax
movl 0x18(%rsp), %ecx
imulq $0x758, %rcx, %rcx      # imm = 0x758
addq %rcx, %rax
cmpb $0x0, 0x49(%rax)
je 0x19ded
movq 0x8(%rsp), %rax
movq 0x9b8(%rax), %rax
movl 0x18(%rsp), %ecx
imulq $0x758, %rcx, %rcx      # imm = 0x758
addq %rcx, %rax
movl $0x1, 0x68(%rax)
jmp 0x19e82
movq 0x8(%rsp), %rax
movq 0x9b8(%rax), %rcx
movl 0x18(%rsp), %edx
imulq $0x758, %rdx, %rdx      # imm = 0x758
addq %rdx, %rcx
movl $0x2, 0x68(%rcx)
movl 0x2e44(%rax), %ecx
cmpl $0x100, 0x2a40(%rax,%rcx,4) # imm = 0x100
jae 0x19e40
leaq 0x91dc(%rip), %rdi      # 0x23004
leaq 0x9d86(%rip), %rsi      # 0x23bb5
movl $0x59a, %edx            # imm = 0x59A
leaq 0x9ff0(%rip), %rcx      # 0x23e2b
callq 0x3160
movq 0x8(%rsp), %rax
movl 0x18(%rsp), %edx
movl 0x2e44(%rax), %ecx
movl %edx, 0x2a40(%rax,%rcx,4)
movl 0x2e44(%rax), %ecx
addl $0x1, %ecx
movl %ecx, 0x2e44(%rax)
cmpl $0x100, 0x2e44(%rax)    # imm = 0x100
jne 0x19e80
movq 0x8(%rsp), %rax
movl $0x0, 0x2e44(%rax)
jmp 0x19e82
jmp 0x19e84
jmp 0x19e86
jmp 0x19e88
movl 0x14(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x14(%rsp)
jmp 0x19d08
jmp 0x19e9a
jmp 0x19e9c
movl 0x18(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x18(%rsp)
jmp 0x19cbf
addq $0x28, %rsp
retq
nopw %cs:(%rax,%rax)