// File: prakhar2808[P]DBEngine/dbengine/memtableWrapper.cc
// Function: memtableWrapper::putKeyValuePair(std::vector<keyValuePair_t, std::allocator<keyValuePair_t>>&, sstableWrapper*, int)
opStatus memtableWrapper::putKeyValuePair(
    std::vector<keyValuePair_t>& keyValuePairVec, 
    sstableWrapper* sstableWrapperObjRef,
    int clientSocket) {
  // Locking to write
  pthread_mutex_lock(&writeMutex);
  // Iterating over the vector and writing.
  for(int i = 0; i < (int)keyValuePairVec.size(); i++) {
    // Put into the memtable
    (*index)->putKeyValuePair(keyValuePairVec[i]);
    // Check if currect memtable is full
    if((*index)->size == (*index)->capacity) {
      std::cout << "Creating new memtable! " << i << std::endl; 
      // New memtable
      memtable* nextMemtableObjPointer = new memtable(0, 
                                                      MAX_MEMTABLE_SIZE,
                                                      lastMemtableID + 1);
      memtableObjPointersList.push_back(nextMemtableObjPointer);
      ++lastMemtableID;
    
      // An async task to put memtable at index to disk and delete entry
      // from list.
      std::thread(writeMemtableToDisk, 
                  index, 
                  sstableWrapperObjRef, 
                  this).detach();
    
      // Make index point to the next memtable.
      ++index;
      std::cout << "Memtable full, switching to next!" << std::endl;
    }
  }
  // Unlocking
  pthread_mutex_unlock(&writeMutex);
  std::string ret = 
    "Inserted " + std::to_string(keyValuePairVec.size()) + " key-value pairs!";
  sendToClient(clientSocket, ret);
  sendEndMsgToClient(clientSocket);
  return opStatus::opSuccess;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x150, %rsp            # imm = 0x150
movq %rdi, -0x8(%rbp)
movq %rsi, -0x10(%rbp)
movq %rdx, -0x18(%rbp)
movl %ecx, -0x1c(%rbp)
movq -0x8(%rbp), %rdi
movq %rdi, -0x110(%rbp)
addq $0x20, %rdi
callq 0x6750
movl $0x0, -0x20(%rbp)
movl -0x20(%rbp), %eax
movl %eax, -0x114(%rbp)
movq -0x10(%rbp), %rdi
callq 0x335c0
movq %rax, %rcx
movl -0x114(%rbp), %eax
cmpl %ecx, %eax
jge 0x364ea
movq -0x110(%rbp), %rdi
addq $0x18, %rdi
callq 0x36c80
movq (%rax), %rax
movq %rax, -0x128(%rbp)
movq -0x10(%rbp), %rdi
movslq -0x20(%rbp), %rsi
callq 0x36dc0
movq %rax, %rsi
leaq -0x60(%rbp), %rdi
movq %rdi, -0x120(%rbp)
callq 0x9830
movq -0x128(%rbp), %rdi
movq -0x120(%rbp), %rsi
callq 0x33e60
jmp 0x36337
leaq -0x60(%rbp), %rdi
callq 0x9890
movq -0x110(%rbp), %rdi
addq $0x18, %rdi
callq 0x36c80
movq -0x110(%rbp), %rdi
movq (%rax), %rax
movl 0x30(%rax), %eax
movl %eax, -0x12c(%rbp)
addq $0x18, %rdi
callq 0x36c80
movq %rax, %rcx
movl -0x12c(%rbp), %eax
movq (%rcx), %rcx
cmpl 0x34(%rcx), %eax
jne 0x364da
movq 0x28c38(%rip), %rdi     # 0x5efc0
leaq 0xaff6(%rip), %rsi      # 0x41385
callq 0x64e0
movq %rax, %rdi
movl -0x20(%rbp), %esi
callq 0x6880
movq %rax, %rdi
movq 0x28be7(%rip), %rsi     # 0x5ef90
callq 0x6540
movl $0x260, %edi            # imm = 0x260
callq 0x64f0
movq %rax, %rdi
movq -0x110(%rbp), %rax
movq %rdi, %rcx
movq %rcx, -0x138(%rbp)
movl 0x48(%rax), %ecx
incl %ecx
xorl %esi, %esi
movl $0x3e8, %edx            # imm = 0x3E8
callq 0x33940
jmp 0x363df
movq -0x110(%rbp), %rdi
movq -0x138(%rbp), %rax
movq %rax, -0x78(%rbp)
leaq -0x78(%rbp), %rsi
callq 0x36bf0
movq -0x110(%rbp), %rax
movl 0x48(%rax), %ecx
incl %ecx
movl %ecx, 0x48(%rax)
movq %rax, %rdx
addq $0x18, %rdx
movq %rax, -0x88(%rbp)
leaq -0x2be(%rip), %rsi      # 0x36160
leaq -0x80(%rbp), %rdi
movq %rdi, -0x140(%rbp)
leaq -0x18(%rbp), %rcx
leaq -0x88(%rbp), %r8
callq 0x36ca0
movq -0x140(%rbp), %rdi
callq 0x68a0
jmp 0x36447
leaq -0x80(%rbp), %rdi
callq 0x36d70
movq -0x110(%rbp), %rdi
addq $0x18, %rdi
callq 0x36da0
movq 0x28b59(%rip), %rdi     # 0x5efc0
leaq 0xaebb(%rip), %rsi      # 0x41329
callq 0x64e0
movq %rax, %rdi
movq 0x28b13(%rip), %rsi     # 0x5ef90
callq 0x6540
jmp 0x364da
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x68(%rbp)
movl %eax, -0x6c(%rbp)
leaq -0x60(%rbp), %rdi
callq 0x9890
jmp 0x3662e
movq -0x138(%rbp), %rdi
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x68(%rbp)
movl %eax, -0x6c(%rbp)
movl $0x260, %esi            # imm = 0x260
callq 0x6500
jmp 0x3662e
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x68(%rbp)
movl %eax, -0x6c(%rbp)
leaq -0x80(%rbp), %rdi
callq 0x36d70
jmp 0x3662e
jmp 0x364dc
movl -0x20(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x20(%rbp)
jmp 0x362c5
movq -0x110(%rbp), %rdi
addq $0x20, %rdi
callq 0x63f0
movq -0x10(%rbp), %rdi
callq 0x335c0
movq %rax, %rsi
leaq -0xe8(%rbp), %rdi
movq %rdi, -0x148(%rbp)
callq 0x36de0
movq -0x148(%rbp), %rdx
leaq 0xae76(%rip), %rsi      # 0x4139d
leaq -0xc8(%rbp), %rdi
callq 0x342e0
jmp 0x36535
leaq 0xae6b(%rip), %rdx      # 0x413a7
leaq -0xa8(%rbp), %rdi
leaq -0xc8(%rbp), %rsi
callq 0x34290
jmp 0x36551
leaq -0xc8(%rbp), %rdi
callq 0x6340
leaq -0xe8(%rbp), %rdi
callq 0x6340
movl -0x1c(%rbp), %eax
movl %eax, -0x14c(%rbp)
leaq -0x108(%rbp), %rdi
leaq -0xa8(%rbp), %rsi
callq 0x6210
jmp 0x36587
movl -0x14c(%rbp), %edi
leaq -0x108(%rbp), %rsi
callq 0x3e3a0
jmp 0x3659b
leaq -0x108(%rbp), %rdi
callq 0x6340
movl -0x1c(%rbp), %edi
callq 0x3e410
jmp 0x365b1
leaq -0xa8(%rbp), %rdi
callq 0x6340
xorl %eax, %eax
addq $0x150, %rsp            # imm = 0x150
popq %rbp
retq
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x68(%rbp)
movl %eax, -0x6c(%rbp)
jmp 0x365ee
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x68(%rbp)
movl %eax, -0x6c(%rbp)
leaq -0xc8(%rbp), %rdi
callq 0x6340
leaq -0xe8(%rbp), %rdi
callq 0x6340
jmp 0x3662e
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x68(%rbp)
movl %eax, -0x6c(%rbp)
jmp 0x36622
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x68(%rbp)
movl %eax, -0x6c(%rbp)
leaq -0x108(%rbp), %rdi
callq 0x6340
leaq -0xa8(%rbp), %rdi
callq 0x6340
movq -0x68(%rbp), %rdi
callq 0x68c0
nopw (%rax,%rax)