// File: /workspace/github_cpp_makefile_star2_O2/gvaumour[P]cache-simulator/src/Cerebron.cc
// Function: CerebronPredictor::checkLazyMigration(CacheEntry*, unsigned long, bool, unsigned long, bool)
CacheEntry*
CerebronPredictor::checkLazyMigration(CacheEntry* current ,uint64_t set,bool inNVM, uint64_t index, bool isWrite)
{
	allocDecision des = activationFunction(isWrite , current->address , current->missPC);

	if( inNVM == false && des == ALLOCATE_IN_NVM)
	{
		//cl is SRAM , check whether we should migrate to NVM 
		if(simu_parameters.enableDatasetSpilling && m_isNVMbusy[set])
		{
			//reportSpilling(rap_current, current->address, false ,  inNVM);
			//stats_busyness_migrate_change++; //If NVM tab is busy , don't migrate
		}
		else
		{
			//Trigger Migration
			int id_assocNVM = evictPolicy(set, true);//Select LRU candidate from NVM cache
			//DPRINTF("DBAMBPredictor:: Migration Triggered from SRAM, index %ld, id_assoc %d \n" , index, id_assoc);

			CacheEntry* replaced_entry_NVM = m_tableNVM[set][id_assocNVM];
					
			/** Migration incurs one read and one extra write */ 
			replaced_entry_NVM->nbWrite++;
			current->nbRead++;
		
			/* Record the write error migration */ 
			Predictor::migrationRecording();
		
			reportMigration(current, false , isWrite);
		
			m_cache->triggerMigration(set, index , id_assocNVM , false);
			if(!m_isWarmup)
				stats_nbMigrations[true]++;


			current = replaced_entry_NVM;
		}

	}
	else if( des == ALLOCATE_IN_SRAM && inNVM == true)
	{
		//cl is in NVM , check whether we should migrate to SRAM 
			
		//If SRAM tab is busy , don't migrate
		if(simu_parameters.enableDatasetSpilling && m_isSRAMbusy[set])
		{
			//reportSpilling(rap_current, current->address, false ,  inNVM);
			//stats_busyness_migrate_change++; //If NVM tab is busy , don't migrate
		}
		else 
		{		
			int id_assocSRAM = evictPolicy(set, false);
		
			CacheEntry* replaced_entry_SRAM = m_tableSRAM[set][id_assocSRAM];

			/** Migration incurs one read and one extra write */ 
			replaced_entry_SRAM->nbWrite++;
			current->nbRead++;
			reportMigration( current, true , isWrite);
	
			m_cache->triggerMigration(set, id_assocSRAM , index , true);
		
			if(!m_isWarmup)
				stats_nbMigrations[false]++;

			current = replaced_entry_SRAM;		
		}

	}
	return current;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
pushq %rax
movl %r9d, %ebp
movq %r8, %r14
movl %ecx, %r13d
movq %rdx, %r15
movq %rsi, %r12
movq %rdi, %rbx
movq 0x8(%rsi), %rdx
movq 0x20(%rsi), %rcx
movl %r9d, %esi
callq 0x6b2e
cmpl $0x1, %eax
setne %cl
orb %r13b, %cl
je 0x82c0
testl %eax, %eax
setne %al
xorb $0x1, %r13b
orb %al, %r13b
jne 0x8368
leaq 0x35d2b(%rip), %rax     # 0x3df50
cmpb $0x1, 0x158(%rax)
jne 0x8246
leaq 0xe8(%rbx), %rdi
movq %r15, %rsi
callq 0x9f66
testq %rdx, (%rax)
jne 0x8368
movq (%rbx), %rax
movq %rbx, %rdi
movl %r15d, %esi
xorl %edx, %edx
callq *0x28(%rax)
movq 0x8(%rbx), %rcx
movq (%rcx), %rcx
imulq $0x18, %r15, %rdx
movslq %eax, %r13
movq (%rcx,%rdx), %rax
movq %r14, (%rsp)
movq (%rax,%r13,8), %r14
incl 0x11c(%r14)
incl 0x120(%r12)
movzbl %bpl, %ecx
pushq $0x1
popq %rbp
movq %rbx, %rdi
movq %r12, %rsi
movl %ebp, %edx
callq 0x8944
movq 0x70(%rbx), %rdi
movl %r15d, %esi
movl %r13d, %edx
movq (%rsp), %rcx
movl %ebp, %r8d
callq 0x163be
cmpb $0x0, 0x81(%rbx)
jne 0x8365
movq 0x4c0(%rbx), %rax
jmp 0x8363
leaq 0x35c89(%rip), %rax     # 0x3df50
cmpb $0x1, 0x158(%rax)
jne 0x82e8
leaq 0x110(%rbx), %rdi
movq %r15, %rsi
callq 0x9f66
testq %rdx, (%rax)
jne 0x8368
movq (%rbx), %rax
pushq $0x1
popq %rdx
movq %rbx, %rdi
movl %r15d, %esi
callq *0x28(%rax)
movq 0x10(%rbx), %rcx
movq (%rcx), %rcx
imulq $0x18, %r15, %rdx
movslq %eax, %r13
movq (%rcx,%rdx), %rax
movq %r14, (%rsp)
movq (%rax,%r13,8), %r14
incl 0x11c(%r14)
incl 0x120(%r12)
movq %rbx, %rdi
callq 0x1fe30
movzbl %bpl, %ecx
movq %rbx, %rdi
movq %r12, %rsi
xorl %edx, %edx
callq 0x8944
movq 0x70(%rbx), %rdi
movl %r15d, %esi
movq (%rsp), %rdx
movl %r13d, %ecx
xorl %r8d, %r8d
callq 0x163be
cmpb $0x0, 0x81(%rbx)
jne 0x8365
movq 0x4c0(%rbx), %rax
addq $0x4, %rax
incl (%rax)
movq %r14, %r12
movq %r12, %rax
addq $0x8, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq