// File: /workspace/github_cpp_makefile_star2_O1/tonymuu[P]distributed-kv-store/Application.cpp
// Function: Application::mp2Run()
void Application::mp2Run() {
	int i;

	// For all the nodes in the system
	for( i = 0; i <= par->EN_GPSZ-1; i++) {

		/*
		 * 1) Update the ring
		 * 2) Receive messages from the network and queue them in the KV store queue
		 */
		if ( par->getcurrtime() > (int)(par->STEP_RATE*i) && !mp2[i]->getMemberNode()->bFailed ) {
			if ( mp2[i]->getMemberNode()->inited && mp2[i]->getMemberNode()->inGroup ) {
				// Step 1
				mp2[i]->updateRing();
			}
			// Step 2
			mp2[i]->recvLoop();
		}
	}

	/**
	 * Handle messages from the queue and update the DHT
	 */
	for ( i = par->EN_GPSZ-1; i >= 0; i-- ) {
		if ( par->getcurrtime() > (int)(par->STEP_RATE*i) && !mp2[i]->getMemberNode()->bFailed ) {
			mp2[i]->checkMessages();
		}
	}

	/**
	 * Insert a set of test key value pairs into the system
	 */
	if ( par->getcurrtime() == INSERT_TIME ) {
		insertTestKVPairs();
	}

	/**
	 * Test CRUD operations
	 */
	if ( par->getcurrtime() >= TEST_TIME ) {
		/**************
		 * CREATE TEST
		 **************/
		/**
		 * TEST 1: Checks if there are RF * NUMBER_OF_INSERTS CREATE SUCCESS message are in the log
		 *
		 */
		if ( par->getcurrtime() == TEST_TIME && CREATE_TEST == par->CRUDTEST ) {
			cout<<endl<<"Doing create test at time: "<<par->getcurrtime()<<endl;
		} // End of create test

		/***************
		 * DELETE TESTS
		 ***************/
		/**
		 * TEST 1: NUMBER_OF_INSERTS/2 Key Value pair are deleted.
		 * 		   Check whether RF * NUMBER_OF_INSERTS/2 DELETE SUCCESS message are in the log
		 * TEST 2: Delete a non-existent key. Check for a DELETE FAIL message in the lgo
		 *
		 */
		else if ( par->getcurrtime() == TEST_TIME && DELETE_TEST == par->CRUDTEST ) {
			deleteTest();
		} // End of delete test

		/*************
		 * READ TESTS
		 *************/
		/**
		 * TEST 1: Read a key. Check for correct value being read in quorum of replicas
		 *
		 * Wait for some time after TEST 1
		 *
		 * TEST 2: Fail a single replica of a key. Check for correct value of the key
		 * 		   being read in quorum of replicas
		 *
		 * Wait for STABILIZE_TIME after TEST 2 (stabilization protocol should ensure at least
		 * 3 replicas for all keys at all times)
		 *
		 * TEST 3 part 1: Fail two replicas of a key. Read the key and check for READ FAIL message in the log.
		 * 				  READ should fail because quorum replicas of the key are not up
		 *
		 * Wait for another STABILIZE_TIME after TEST 3 part 1 (stabilization protocol should ensure at least
		 * 3 replicas for all keys at all times)
		 *
		 * TEST 3 part 2: Read the same key as TEST 3 part 1. Check for correct value of the key
		 * 		  		  being read in quorum of replicas
		 *
		 * Wait for some time after TEST 3 part 2
		 *
		 * TEST 4: Fail a non-replica. Check for correct value of the key
		 * 		   being read in quorum of replicas
		 *
		 * TEST 5: Read a non-existent key. Check for a READ FAIL message in the log
		 *
		 */
		else if ( par->getcurrtime() >= TEST_TIME && READ_TEST == par->CRUDTEST ) {
			readTest();
		} // end of read test

		/***************
		 * UPDATE TESTS
		 ***************/
		/**
		 * TEST 1: Update a key. Check for correct new value being updated in quorum of replicas
		 *
		 * Wait for some time after TEST 1
		 *
		 * TEST 2: Fail a single replica of a key. Update the key. Check for correct new value of the key
		 * 		   being updated in quorum of replicas
		 *
		 * Wait for STABILIZE_TIME after TEST 2 (stabilization protocol should ensure at least
		 * 3 replicas for all keys at all times)
		 *
		 * TEST 3 part 1: Fail two replicas of a key. Update the key and check for READ FAIL message in the log
		 * 				  UPDATE should fail because quorum replicas of the key are not up
		 *
		 * Wait for another STABILIZE_TIME after TEST 3 part 1 (stabilization protocol should ensure at least
		 * 3 replicas for all keys at all times)
		 *
		 * TEST 3 part 2: Update the same key as TEST 3 part 1. Check for correct new value of the key
		 * 		   		  being update in quorum of replicas
		 *
		 * Wait for some time after TEST 3 part 2
		 *
		 * TEST 4: Fail a non-replica. Check for correct new value of the key
		 * 		   being updated in quorum of replicas
		 *
		 * TEST 5: Update a non-existent key. Check for a UPDATE FAIL message in the log
		 *
		 */
		else if ( par->getcurrtime() >= TEST_TIME && UPDATE_TEST == par->CRUDTEST ) {
			updateTest();
		} // End of update test

	} // end of if ( par->getcurrtime == TEST_TIME)
}

// Assembly:
pushq %r15
pushq %r14
pushq %rbx
movq %rdi, %rbx
movq 0x58(%rdi), %rdi
movl 0x18(%rdi), %eax
testl %eax, %eax
jle 0x745a
xorl %r14d, %r14d
callq 0xc962
movq 0x58(%rbx), %rcx
xorps %xmm0, %xmm0
cvtsi2sd %r14d, %xmm0
mulsd 0x10(%rcx), %xmm0
cvttsd2si %xmm0, %ecx
cmpl %ecx, %eax
jle 0x744a
movq 0x48(%rbx), %rax
movq (%rax,%r14,8), %rdi
movq 0x50(%rdi), %rax
cmpb $0x0, 0x10(%rax)
jne 0x744a
cmpb $0x1, 0xe(%rax)
jne 0x743d
cmpb $0x1, 0xf(%rax)
jne 0x743d
callq 0xe8e4
movq 0x48(%rbx), %rax
movq (%rax,%r14,8), %rdi
callq 0x1271e
incq %r14
movq 0x58(%rbx), %rdi
movslq 0x18(%rdi), %rax
cmpq %rax, %r14
jl 0x73fc
testl %eax, %eax
jle 0x74ab
movl %eax, %r14d
movq %r14, %r15
decq %r14
movq 0x58(%rbx), %rdi
callq 0xc962
movq 0x58(%rbx), %rcx
xorps %xmm0, %xmm0
cvtsi2sd %r14d, %xmm0
mulsd 0x10(%rcx), %xmm0
cvttsd2si %xmm0, %ecx
cmpl %ecx, %eax
jle 0x74a1
movq 0x48(%rbx), %rax
movq -0x8(%rax,%r15,8), %rdi
movq 0x50(%rdi), %rax
cmpb $0x0, 0x10(%rax)
jne 0x74a1
callq 0x1108a
leaq 0x1(%r14), %rax
cmpq $0x1, %rax
jg 0x7461
movq 0x58(%rbx), %rdi
callq 0xc962
cmpl $0x64, %eax
jne 0x74c1
movq %rbx, %rdi
callq 0x75f2
movq 0x58(%rbx), %rdi
callq 0xc962
cmpl $0x96, %eax
jl 0x7564
movq 0x58(%rbx), %rdi
callq 0xc962
cmpl $0x96, %eax
jne 0x74ef
movq 0x58(%rbx), %rax
cmpl $0x0, 0x34(%rax)
je 0x756a
movq 0x58(%rbx), %rdi
callq 0xc962
cmpl $0x96, %eax
jne 0x7516
movq 0x58(%rbx), %rax
cmpl $0x3, 0x34(%rax)
jne 0x7516
movq %rbx, %rdi
popq %rbx
popq %r14
popq %r15
jmp 0x7800
movq 0x58(%rbx), %rdi
callq 0xc962
cmpl $0x96, %eax
jl 0x753d
movq 0x58(%rbx), %rax
cmpl $0x1, 0x34(%rax)
jne 0x753d
movq %rbx, %rdi
popq %rbx
popq %r14
popq %r15
jmp 0x7b32
movq 0x58(%rbx), %rdi
callq 0xc962
cmpl $0x96, %eax
jl 0x7564
movq 0x58(%rbx), %rax
cmpl $0x2, 0x34(%rax)
jne 0x7564
movq %rbx, %rdi
popq %rbx
popq %r14
popq %r15
jmp 0x929c
popq %rbx
popq %r14
popq %r15
retq
movq 0x19a57(%rip), %r14     # 0x20fc8
movq (%r14), %rax
movq -0x18(%rax), %rdi
addq %r14, %rdi
movl $0xa, %esi
callq 0x3280
movsbl %al, %esi
movq %r14, %rdi
callq 0x3030
movq %rax, %rdi
callq 0x31c0
movq %rax, %r14
leaq 0x10d46(%rip), %rsi     # 0x182e8
movl $0x1b, %edx
movq %rax, %rdi
callq 0x3310
movq 0x58(%rbx), %rdi
callq 0xc962
movq %r14, %rdi
movl %eax, %esi
callq 0x3490
movq %rax, %rbx
movq (%rax), %rax
movq -0x18(%rax), %rdi
addq %rbx, %rdi
movl $0xa, %esi
callq 0x3280
movsbl %al, %esi
movq %rbx, %rdi
callq 0x3030
movq %rax, %rdi
popq %rbx
popq %r14
popq %r15
jmp 0x31c0
nop