// File: gvaumour[P]cache-simulator/src/DBAMBPredictor.cc
// Function: DBAMBPredictor::DBAMBPredictor(int, int, int, int, std::vector<std::vector<CacheEntry*, std::allocator<CacheEntry*>>, std::allocator<std::vector<CacheEntry*, std::allocator<CacheEntry*>>>>&, std::vector<std::vector<CacheEntry*, std::allocator<CacheEntry*>>, std::allocator<std::vector<CacheEntry*, std::allocator<CacheEntry*>>>>&, HybridCache*)
DBAMBPredictor::DBAMBPredictor(int id, int nbAssoc , int nbSet, int nbNVMways, DataArray& SRAMtable, DataArray& NVMtable, HybridCache* cache) : \
	Predictor(id, nbAssoc, nbSet, nbNVMways, SRAMtable, NVMtable, cache) {

	m_cpt = 1;
	m_RAP_assoc = simu_parameters.rap_assoc;
	m_RAP_sets = simu_parameters.rap_sets;

	m_DHPTable.clear();
	m_DHPTable.resize(m_RAP_sets);
	
	for(unsigned i = 0 ; i < m_RAP_sets ; i++)
	{
		m_DHPTable[i].resize(m_RAP_assoc);
		
		
		for(unsigned j = 0 ; j < m_RAP_assoc ; j++)
		{
			m_DHPTable[i][j] = new DHPEntry();
			m_DHPTable[i][j]->index = i;
			m_DHPTable[i][j]->assoc = j;
		}
	}
	/*
	if(simu_parameters.enableReuseErrorComputation)
		stats_history_SRAM.resize(nbSet);
	*/

	if(simu_parameters.DBAMB_signature.find("B") != std::string::npos)
	{	
		vector<string> split_line = split(simu_parameters.DBAMB_signature , 'B');
	
		if(split_line.size() != 0)
		{
			for(auto byte : split_line)
				m_hashingBytes.push_back(atoi(byte.c_str()));
			
			for(auto byte : m_hashingBytes)
				cout << "Hashing Function - Byte : " << byte << "B" << endl;
	
		}

	}

	
	//DPRINTF("RAPPredictor::Constructor m_DHPTable.size() = %lu , m_DHPTable[0].size() = %lu\n" , m_DHPTable.size() , m_DHPTable[0].size());

	m_rap_policy = new DBAMBLRUPolicy(m_RAP_assoc , m_RAP_sets , m_DHPTable);

	/* Stats init*/ 
	stats_nbSwitchDst.clear();
	stats_ClassErrors.clear();
	stats_ClassErrors = vector< vector<int> >(NUM_RW_TYPE*NUM_RD_TYPE, vector<int>(NUM_RD_TYPE*NUM_RW_TYPE, 0));	
	

	if(simu_parameters.printDebug)
		dataset_file.open(RAP_TEST_OUTPUT_DATASETS);
	
	stats_nbMigrationsFromNVM.push_back(vector<int>(2,0));

	m_costParameters = simu_parameters.optTarget;
	
	if(simu_parameters.ratio_RWcost != -1)
		m_costParameters.costNVM[WRITE_ACCESS] = m_costParameters.costNVM[READ_ACCESS]*simu_parameters.ratio_RWcost;
	
	stats_error_wrongallocation = 0;
	stats_error_learning = 0;
	stats_error_wrongpolicy = 0;	

	stats_error_SRAMwrongallocation = 0;
	stats_error_SRAMlearning = 0;
	stats_error_SRAMwrongpolicy = 0;

	stats_allocate_NVM = 0, stats_allocate_SRAM = 0;
	stats_busyness_alloc_change = 0, stats_busyness_migrate_change = 0;
}

// Assembly:
subq $0x1e8, %rsp            # imm = 0x1E8
movq 0x1f8(%rsp), %rax
movq 0x1f0(%rsp), %rax
movq %rdi, 0x1e0(%rsp)
movl %esi, 0x1dc(%rsp)
movl %edx, 0x1d8(%rsp)
movl %ecx, 0x1d4(%rsp)
movl %r8d, 0x1d0(%rsp)
movq %r9, 0x1c8(%rsp)
movq 0x1e0(%rsp), %rdi
movq %rdi, 0xb0(%rsp)
movl 0x1dc(%rsp), %esi
movl 0x1d8(%rsp), %edx
movl 0x1d4(%rsp), %ecx
movl 0x1d0(%rsp), %r8d
movq 0x1c8(%rsp), %r9
movq 0x1f0(%rsp), %r10
movq 0x1f8(%rsp), %r11
movq %rsp, %rax
movq %r11, 0x8(%rax)
movq %r10, (%rax)
callq 0x537e0
movq 0xb0(%rsp), %rdi
leaq 0x78919(%rip), %rax     # 0x92630
movq %rax, (%rdi)
addq $0x280, %rdi            # imm = 0x280
movq %rdi, 0xa8(%rsp)
callq 0x5540
movq 0xb0(%rsp), %rdi
addq $0x2a0, %rdi            # imm = 0x2A0
movq %rdi, 0xb8(%rsp)
callq 0xe880
jmp 0x19d4c
movq 0xb0(%rsp), %rdi
addq $0x2e8, %rdi            # imm = 0x2E8
movq %rdi, 0xa0(%rsp)
callq 0x20180
movq 0xb0(%rsp), %rdi
addq $0x308, %rdi            # imm = 0x308
movq %rdi, 0x70(%rsp)
callq 0x20190
movq 0xb0(%rsp), %rdi
addq $0x340, %rdi            # imm = 0x340
movq %rdi, 0x78(%rsp)
callq 0xe8d0
movq 0xb0(%rsp), %rdi
addq $0x388, %rdi            # imm = 0x388
movq %rdi, 0x80(%rsp)
callq 0xe8e0
movq 0xb0(%rsp), %rdi
addq $0x3a0, %rdi            # imm = 0x3A0
movq %rdi, 0x88(%rsp)
callq 0xe860
movq 0xb0(%rsp), %rdi
addq $0x3b8, %rdi            # imm = 0x3B8
movq %rdi, 0x90(%rsp)
callq 0xe860
movq 0xb0(%rsp), %rdi
addq $0x3d0, %rdi            # imm = 0x3D0
movq %rdi, 0x98(%rsp)
callq 0x201a0
movq 0xb0(%rsp), %rax
movq 0xa0(%rsp), %rdi
movq $0x1, 0x270(%rax)
leaq 0x7a1c4(%rip), %rcx     # 0x93ff0
movl 0xac(%rcx), %edx
movl %edx, 0x338(%rax)
movl 0xb0(%rcx), %ecx
movl %ecx, 0x33c(%rax)
callq 0x201b0
movq 0xb0(%rsp), %rax
movq 0xa0(%rsp), %rdi
movl 0x33c(%rax), %eax
movl %eax, %esi
callq 0x201d0
jmp 0x19e68
movl $0x0, 0x1b8(%rsp)
movq 0xb0(%rsp), %rcx
movl 0x1b8(%rsp), %eax
cmpl 0x33c(%rcx), %eax
jae 0x1a047
movq 0xb0(%rsp), %rdi
addq $0x2e8, %rdi            # imm = 0x2E8
movl 0x1b8(%rsp), %eax
movl %eax, %esi
callq 0x20270
movq %rax, %rdi
movq 0xb0(%rsp), %rax
movl 0x338(%rax), %eax
movl %eax, %esi
callq 0x20290
jmp 0x19ec5
movl $0x0, 0x1b4(%rsp)
movq 0xb0(%rsp), %rcx
movl 0x1b4(%rsp), %eax
cmpl 0x338(%rcx), %eax
jae 0x1a02f
movl $0xc0, %edi
callq 0x53a0
movq %rax, 0x68(%rsp)
jmp 0x19efc
movq 0x68(%rsp), %rdi
callq 0x20330
jmp 0x19f08
movq 0xb0(%rsp), %rdi
addq $0x2e8, %rdi            # imm = 0x2E8
movl 0x1b8(%rsp), %eax
movl %eax, %esi
callq 0x20270
movq %rax, %rdi
movl 0x1b4(%rsp), %eax
movl %eax, %esi
callq 0x20430
movq 0x68(%rsp), %rcx
movq 0xb0(%rsp), %rdi
movq %rcx, (%rax)
movl 0x1b8(%rsp), %eax
movl %eax, 0x60(%rsp)
addq $0x2e8, %rdi            # imm = 0x2E8
movl 0x1b8(%rsp), %eax
movl %eax, %esi
callq 0x20270
movq %rax, %rdi
movl 0x1b4(%rsp), %eax
movl %eax, %esi
callq 0x20430
movl 0x60(%rsp), %ecx
movq 0xb0(%rsp), %rdi
movq (%rax), %rax
movl %ecx, 0x30(%rax)
movl 0x1b4(%rsp), %eax
movl %eax, 0x64(%rsp)
addq $0x2e8, %rdi            # imm = 0x2E8
movl 0x1b8(%rsp), %eax
movl %eax, %esi
callq 0x20270
movq %rax, %rdi
movl 0x1b4(%rsp), %eax
movl %eax, %esi
callq 0x20430
movl 0x64(%rsp), %ecx
movq (%rax), %rax
movl %ecx, 0x34(%rax)
movl 0x1b4(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x1b4(%rsp)
jmp 0x19ed0
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
jmp 0x1a724
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
jmp 0x1a6c2
movq 0x68(%rsp), %rdi
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
callq 0x5340
jmp 0x1a6c2
jmp 0x1a031
movl 0x1b8(%rsp), %eax
addl $0x1, %eax
movl %eax, 0x1b8(%rsp)
jmp 0x19e73
leaq 0x79fa2(%rip), %rdi     # 0x93ff0
addq $0x130, %rdi            # imm = 0x130
leaq 0x5832e(%rip), %rsi     # 0x7238a
xorl %eax, %eax
movl %eax, %edx
callq 0x5740
cmpq $-0x1, %rax
je 0x1a312
leaq 0x79f7a(%rip), %rsi     # 0x93ff0
addq $0x130, %rsi            # imm = 0x130
leaq 0x178(%rsp), %rdi
callq 0x51b0
jmp 0x1a08c
leaq 0x198(%rsp), %rdi
leaq 0x178(%rsp), %rsi
movl $0x42, %edx
callq 0x653b0
jmp 0x1a0a8
leaq 0x178(%rsp), %rdi
callq 0x5768
leaq 0x198(%rsp), %rdi
callq 0xf190
cmpq $0x0, %rax
je 0x1a2f1
leaq 0x198(%rsp), %rax
movq %rax, 0x170(%rsp)
movq 0x170(%rsp), %rdi
callq 0xebf0
movq %rax, 0x168(%rsp)
movq 0x170(%rsp), %rdi
callq 0xec20
movq %rax, 0x160(%rsp)
leaq 0x168(%rsp), %rdi
leaq 0x160(%rsp), %rsi
callq 0xec50
testb $0x1, %al
jne 0x1a124
jmp 0x1a20a
leaq 0x168(%rsp), %rdi
callq 0xec90
movq %rax, %rsi
leaq 0x140(%rsp), %rdi
callq 0x51b0
jmp 0x1a143
movq 0xb0(%rsp), %rax
addq $0x340, %rax            # imm = 0x340
movq %rax, 0x58(%rsp)
leaq 0x140(%rsp), %rdi
callq 0x51a0
movq %rax, %rdi
callq 0x55b0
movq 0x58(%rsp), %rdi
movl %eax, 0x13c(%rsp)
leaq 0x13c(%rsp), %rsi
callq 0x20450
jmp 0x1a186
leaq 0x140(%rsp), %rdi
callq 0x5768
leaq 0x168(%rsp), %rdi
callq 0xeca0
jmp 0x1a106
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
leaq 0x178(%rsp), %rdi
callq 0x5768
jmp 0x1a6c2
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
jmp 0x1a300
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
leaq 0x140(%rsp), %rdi
callq 0x5768
jmp 0x1a300
movq 0xb0(%rsp), %rax
addq $0x340, %rax            # imm = 0x340
movq %rax, 0x130(%rsp)
movq 0x130(%rsp), %rdi
callq 0x112d0
movq %rax, 0x128(%rsp)
movq 0x130(%rsp), %rdi
callq 0x11300
movq %rax, 0x120(%rsp)
leaq 0x128(%rsp), %rdi
leaq 0x120(%rsp), %rsi
callq 0x20480
testb $0x1, %al
jne 0x1a268
jmp 0x1a2ef
leaq 0x128(%rsp), %rdi
callq 0x204c0
movl (%rax), %eax
movl %eax, 0x11c(%rsp)
movq 0x78d4b(%rip), %rdi     # 0x92fd0
leaq 0x576fc(%rip), %rsi     # 0x71988
callq 0x5380
movq %rax, 0x50(%rsp)
jmp 0x1a298
movq 0x50(%rsp), %rdi
movl 0x11c(%rsp), %esi
callq 0x5680
movq %rax, 0x48(%rsp)
jmp 0x1a2b0
movq 0x48(%rsp), %rdi
leaq 0x580ce(%rip), %rsi     # 0x7238a
callq 0x5380
movq %rax, 0x40(%rsp)
jmp 0x1a2c8
movq 0x40(%rsp), %rdi
movq 0x78ce4(%rip), %rsi     # 0x92fb8
callq 0x53d0
jmp 0x1a2db
jmp 0x1a2dd
leaq 0x128(%rsp), %rdi
callq 0x204d0
jmp 0x1a24a
jmp 0x1a2f1
leaq 0x198(%rsp), %rdi
callq 0xf560
jmp 0x1a312
leaq 0x198(%rsp), %rdi
callq 0xf560
jmp 0x1a6c2
movl $0x28, %edi
callq 0x53a0
movq %rax, 0x38(%rsp)
jmp 0x1a323
movq 0x38(%rsp), %rdi
movq 0xb0(%rsp), %rcx
movl 0x338(%rcx), %esi
movl 0x33c(%rcx), %edx
addq $0x2e8, %rcx            # imm = 0x2E8
callq 0x1ff70
jmp 0x1a34a
movq 0xb0(%rsp), %rdi
movq 0x38(%rsp), %rax
movq %rax, 0x300(%rdi)
addq $0x388, %rdi            # imm = 0x388
callq 0xfc90
movq 0xb0(%rsp), %rdi
addq $0x3a0, %rdi            # imm = 0x3A0
callq 0x204f0
movl $0x0, 0xe4(%rsp)
leaq 0xe3(%rsp), %rdi
movq %rdi, 0x30(%rsp)
callq 0xed30
movq 0x30(%rsp), %rcx
leaq 0xe8(%rsp), %rdi
movl $0xf, %esi
leaq 0xe4(%rsp), %rdx
callq 0xed40
jmp 0x1a3bc
leaq 0xe2(%rsp), %rdi
movq %rdi, 0x28(%rsp)
callq 0xedc0
movq 0x28(%rsp), %rcx
leaq 0x100(%rsp), %rdi
movl $0xf, %esi
leaq 0xe8(%rsp), %rdx
callq 0xedd0
jmp 0x1a3ef
movq 0xb0(%rsp), %rdi
addq $0x3a0, %rdi            # imm = 0x3A0
leaq 0x100(%rsp), %rsi
callq 0xee50
leaq 0x100(%rsp), %rdi
callq 0xee90
leaq 0xe2(%rsp), %rdi
callq 0xeef0
leaq 0xe8(%rsp), %rdi
callq 0xef00
leaq 0xe3(%rsp), %rdi
callq 0xef60
leaq 0x79baa(%rip), %rax     # 0x93ff0
testb $0x1, (%rax)
je 0x1a4e4
leaq 0x792b2(%rip), %rdi     # 0x93708
leaq 0x57546(%rip), %rsi     # 0x719a3
movl $0x10, %edx
callq 0x5070
jmp 0x1a469
jmp 0x1a4e4
movq 0x38(%rsp), %rdi
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
callq 0x5340
jmp 0x1a6c2
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
jmp 0x1a4d2
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
leaq 0xe2(%rsp), %rdi
callq 0xeef0
leaq 0xe8(%rsp), %rdi
callq 0xef00
leaq 0xe3(%rsp), %rdi
callq 0xef60
jmp 0x1a6c2
movq 0xb0(%rsp), %rax
addq $0x3b8, %rax            # imm = 0x3B8
movq %rax, 0x18(%rsp)
movl $0x0, 0xc4(%rsp)
leaq 0xc3(%rsp), %rdi
movq %rdi, 0x20(%rsp)
callq 0xed30
movq 0x20(%rsp), %rcx
leaq 0xc8(%rsp), %rdi
movl $0x2, %esi
leaq 0xc4(%rsp), %rdx
callq 0xed40
jmp 0x1a535
movq 0x18(%rsp), %rdi
leaq 0xc8(%rsp), %rsi
callq 0x20510
jmp 0x1a549
leaq 0xc8(%rsp), %rdi
callq 0xef00
leaq 0xc3(%rsp), %rdi
callq 0xef60
movq 0xb0(%rsp), %rdi
addq $0x2a0, %rdi            # imm = 0x2A0
leaq 0x79a77(%rip), %rsi     # 0x93ff0
addq $0xe8, %rsi
callq 0xefb0
jmp 0x1a587
leaq 0x79a62(%rip), %rax     # 0x93ff0
movss 0xe0(%rax), %xmm0
movss 0x573de(%rip), %xmm1    # 0x7197c
ucomiss %xmm1, %xmm0
jne 0x1a5aa
jp 0x1a5aa
jmp 0x1a644
movq 0xb0(%rsp), %rdi
addq $0x2a0, %rdi            # imm = 0x2A0
xorl %eax, %eax
movl %eax, %esi
callq 0xef90
movq 0xb0(%rsp), %rdi
cvtsi2ssl (%rax), %xmm0
leaq 0x79a1b(%rip), %rax     # 0x93ff0
mulss 0xe0(%rax), %xmm0
cvttss2si %xmm0, %eax
movl %eax, 0x14(%rsp)
addq $0x2a0, %rdi            # imm = 0x2A0
movl $0x1, %esi
callq 0xef90
movl 0x14(%rsp), %ecx
movl %ecx, (%rax)
jmp 0x1a644
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
jmp 0x1a635
movq %rax, %rcx
movl %edx, %eax
movq %rcx, 0x1c0(%rsp)
movl %eax, 0x1bc(%rsp)
leaq 0xc8(%rsp), %rdi
callq 0xef00
leaq 0xc3(%rsp), %rdi
callq 0xef60
jmp 0x1a6c2
movq 0xb0(%rsp), %rax
movq $0x0, 0x3e8(%rax)
movq $0x0, 0x3f0(%rax)
movq $0x0, 0x3f8(%rax)
movq $0x0, 0x400(%rax)
movq $0x0, 0x408(%rax)
movq $0x0, 0x410(%rax)
movq $0x0, 0x360(%rax)
movq $0x0, 0x368(%rax)
movq $0x0, 0x378(%rax)
movq $0x0, 0x380(%rax)
addq $0x1e8, %rsp            # imm = 0x1E8
retq
movq 0x98(%rsp), %rdi
callq 0x20540
movq 0x90(%rsp), %rdi
callq 0xee90
movq 0x88(%rsp), %rdi
callq 0xee90
movq 0x80(%rsp), %rdi
callq 0xf460
movq 0x78(%rsp), %rdi
callq 0xef00
movq 0x70(%rsp), %rdi
callq 0x205a0
movq 0xa0(%rsp), %rdi
callq 0x205b0
movq 0xb8(%rsp), %rdi
callq 0xf520
movq 0xa8(%rsp), %rdi
callq 0x5768
movq 0xb0(%rsp), %rdi
callq 0x549b0
movq 0x1c0(%rsp), %rdi
callq 0x5690
nopl (%rax,%rax)