// File: /workspace/github_cpp_makefile_star2_O1/HQarroum[P]thread-pool/examples/many-producers-many-consumers/./../../includes/concurrent_queue.hpp
// Function: bool moodycamel::ConcurrentQueue<std::function<void ()>, moodycamel::ConcurrentQueueDefaultTraits>::ImplicitProducer::enqueue_bulk<(moodycamel::ConcurrentQueue<std::function<void ()>, moodycamel::ConcurrentQueueDefaultTraits>::AllocationMode)0, std::function<void ()> const*>(std::function<void ()> const*, unsigned long)
bool enqueue_bulk(It itemFirst, size_t count)
		{
			// First, we need to make sure we have enough room to enqueue all of the elements;
			// this means pre-allocating blocks and putting them in the block index (but only if
			// all the allocations succeeded).
			
			// Note that the tailBlock we start off with may not be owned by us any more;
			// this happens if it was filled up exactly to the top (setting tailIndex to
			// the first index of the next block which is not yet allocated), then dequeued
			// completely (putting it on the free list) before we enqueue again.
			
			index_t startTailIndex = this->tailIndex.load(std::memory_order_relaxed);
			auto startBlock = this->tailBlock;
			Block* firstAllocatedBlock = nullptr;
			auto endBlock = this->tailBlock;
			
			// Figure out how many blocks we'll need to allocate, and do so
			size_t blockBaseDiff = ((startTailIndex + count - 1) & ~static_cast<index_t>(BLOCK_SIZE - 1)) - ((startTailIndex - 1) & ~static_cast<index_t>(BLOCK_SIZE - 1));
			index_t currentTailIndex = (startTailIndex - 1) & ~static_cast<index_t>(BLOCK_SIZE - 1);
			if (blockBaseDiff > 0) {
#ifdef MCDBGQ_NOLOCKFREE_IMPLICITPRODBLOCKINDEX
				debug::DebugLock lock(mutex);
#endif
				do {
					blockBaseDiff -= static_cast<index_t>(BLOCK_SIZE);
					currentTailIndex += static_cast<index_t>(BLOCK_SIZE);
					
					// Find out where we'll be inserting this block in the block index
					BlockIndexEntry* idxEntry = nullptr;  // initialization here unnecessary but compiler can't always tell
					Block* newBlock;
					bool indexInserted = false;
					auto head = this->headIndex.load(std::memory_order_relaxed);
					assert(!details::circular_less_than<index_t>(currentTailIndex, head));
					bool full = !details::circular_less_than<index_t>(head, currentTailIndex + BLOCK_SIZE) || (MAX_SUBQUEUE_SIZE != details::const_numeric_max<size_t>::value && (MAX_SUBQUEUE_SIZE == 0 || MAX_SUBQUEUE_SIZE - BLOCK_SIZE < currentTailIndex - head));

					if (full || !(indexInserted = insert_block_index_entry<allocMode>(idxEntry, currentTailIndex)) || (newBlock = this->parent->ConcurrentQueue::template requisition_block<allocMode>()) == nullptr) {
						// Index allocation or block allocation failed; revert any other allocations
						// and index insertions done so far for this operation
						if (indexInserted) {
							rewind_block_index_tail();
							idxEntry->value.store(nullptr, std::memory_order_relaxed);
						}
						currentTailIndex = (startTailIndex - 1) & ~static_cast<index_t>(BLOCK_SIZE - 1);
						for (auto block = firstAllocatedBlock; block != nullptr; block = block->next) {
							currentTailIndex += static_cast<index_t>(BLOCK_SIZE);
							idxEntry = get_block_index_entry_for_index(currentTailIndex);
							idxEntry->value.store(nullptr, std::memory_order_relaxed);
							rewind_block_index_tail();
						}
						this->parent->add_blocks_to_free_list(firstAllocatedBlock);
						this->tailBlock = startBlock;
						
						return false;
					}
					
#ifdef MCDBGQ_TRACKMEM
					newBlock->owner = this;
#endif
					newBlock->ConcurrentQueue::Block::template reset_empty<implicit_context>();
					newBlock->next = nullptr;
					
					// Insert the new block into the index
					idxEntry->value.store(newBlock, std::memory_order_relaxed);
					
					// Store the chain of blocks so that we can undo if later allocations fail,
					// and so that we can find the blocks when we do the actual enqueueing
					if ((startTailIndex & static_cast<index_t>(BLOCK_SIZE - 1)) != 0 || firstAllocatedBlock != nullptr) {
						assert(this->tailBlock != nullptr);
						this->tailBlock->next = newBlock;
					}
					this->tailBlock = newBlock;
					endBlock = newBlock;
					firstAllocatedBlock = firstAllocatedBlock == nullptr ? newBlock : firstAllocatedBlock;
				} while (blockBaseDiff > 0);
			}
			
			// Enqueue, one block at a time
			index_t newTailIndex = startTailIndex + static_cast<index_t>(count);
			currentTailIndex = startTailIndex;
			this->tailBlock = startBlock;
			assert((startTailIndex & static_cast<index_t>(BLOCK_SIZE - 1)) != 0 || firstAllocatedBlock != nullptr || count == 0);
			if ((startTailIndex & static_cast<index_t>(BLOCK_SIZE - 1)) == 0 && firstAllocatedBlock != nullptr) {
				this->tailBlock = firstAllocatedBlock;
			}
			while (true) {
				index_t stopIndex = (currentTailIndex & ~static_cast<index_t>(BLOCK_SIZE - 1)) + static_cast<index_t>(BLOCK_SIZE);
				if (details::circular_less_than<index_t>(newTailIndex, stopIndex)) {
					stopIndex = newTailIndex;
				}
				MOODYCAMEL_CONSTEXPR_IF (MOODYCAMEL_NOEXCEPT_CTOR(T, decltype(*itemFirst), new (static_cast<T*>(nullptr)) T(details::deref_noexcept(itemFirst)))) {
					while (currentTailIndex != stopIndex) {
						new ((*this->tailBlock)[currentTailIndex++]) T(*itemFirst++);
					}
				}
				else {
					MOODYCAMEL_TRY {
						while (currentTailIndex != stopIndex) {
							new ((*this->tailBlock)[currentTailIndex]) T(details::nomove_if<!MOODYCAMEL_NOEXCEPT_CTOR(T, decltype(*itemFirst), new (static_cast<T*>(nullptr)) T(details::deref_noexcept(itemFirst)))>::eval(*itemFirst));
							++currentTailIndex;
							++itemFirst;
						}
					}
					MOODYCAMEL_CATCH (...) {
						auto constructedStopIndex = currentTailIndex;
						auto lastBlockEnqueued = this->tailBlock;
						
						if (!details::is_trivially_destructible<T>::value) {
							auto block = startBlock;
							if ((startTailIndex & static_cast<index_t>(BLOCK_SIZE - 1)) == 0) {
								block = firstAllocatedBlock;
							}
							currentTailIndex = startTailIndex;
							while (true) {
								stopIndex = (currentTailIndex & ~static_cast<index_t>(BLOCK_SIZE - 1)) + static_cast<index_t>(BLOCK_SIZE);
								if (details::circular_less_than<index_t>(constructedStopIndex, stopIndex)) {
									stopIndex = constructedStopIndex;
								}
								while (currentTailIndex != stopIndex) {
									(*block)[currentTailIndex++]->~T();
								}
								if (block == lastBlockEnqueued) {
									break;
								}
								block = block->next;
							}
						}
						
						currentTailIndex = (startTailIndex - 1) & ~static_cast<index_t>(BLOCK_SIZE - 1);
						for (auto block = firstAllocatedBlock; block != nullptr; block = block->next) {
							currentTailIndex += static_cast<index_t>(BLOCK_SIZE);
							auto idxEntry = get_block_index_entry_for_index(currentTailIndex);
							idxEntry->value.store(nullptr, std::memory_order_relaxed);
							rewind_block_index_tail();
						}
						this->parent->add_blocks_to_free_list(firstAllocatedBlock);
						this->tailBlock = startBlock;
						MOODYCAMEL_RETHROW;
					}
				}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x48, %rsp
movq %rsi, %r15
movq %rdi, %r12
movabsq $-0x8000000000000000, %rsi # imm = 0x8000000000000000
movq 0x20(%rdi), %rbx
movq 0x40(%rdi), %rcx
movq %rdx, 0x38(%rsp)
leaq (%rbx,%rdx), %r13
decq %r13
andq $-0x20, %r13
leaq -0x1(%rbx), %rax
andq $-0x20, %rax
subq %rax, %r13
movq %rdi, 0x10(%rsp)
movq %rcx, 0x28(%rsp)
movq %rax, 0x40(%rsp)
je 0x6fd0
leaq 0x20(%rax), %r10
movq $0x0, 0x8(%rsp)
leaq -0x1(%rsi), %r11
movq %rcx, 0x30(%rsp)
movq %r10, 0x20(%rsp)
movq %r11, 0x18(%rsp)
leaq 0x20(%rax), %rbp
movq 0x28(%r12), %rcx
movq %rbp, %rdx
subq %rcx, %rdx
movabsq $-0x8000000000000000, %rsi # imm = 0x8000000000000000
cmpq %rsi, %rdx
ja 0x70d1
subq %rax, %rcx
leaq (%rsi,%rcx), %rax
addq $-0x41, %rax
cmpq %r11, %rax
jae 0x6ea1
movq 0x10(%rsp), %r12
movq 0x60(%r12), %rax
testq %rax, %rax
je 0x6dcf
movq 0x8(%rax), %rdx
incq %rdx
movq (%rax), %rcx
movq 0x18(%rax), %rsi
decq %rcx
andq %rdx, %rcx
movq (%rsi,%rcx,8), %r14
movq (%r14), %rdx
cmpq $0x1, %rdx
je 0x6dc3
movq 0x8(%r14), %rdx
testq %rdx, %rdx
je 0x6dc3
movq %r12, %rdi
callq 0x5422
testb %al, %al
je 0x6dd7
movq 0x60(%r12), %rax
movq 0x8(%rax), %rdx
incq %rdx
movq (%rax), %rcx
movq 0x18(%rax), %rsi
decq %rcx
andq %rdx, %rcx
movq (%rsi,%rcx,8), %r14
movq (%r14), %rdx
cmpq $0x1, %rdx
movq 0x20(%rsp), %r10
movq 0x18(%rsp), %r11
jne 0x714d
movq %rbp, (%r14)
movq %rcx, 0x8(%rax)
movb $0x1, %r12b
jmp 0x6de4
xorl %r14d, %r14d
xorl %r12d, %r12d
jmp 0x6de4
xorl %r12d, %r12d
movq 0x20(%rsp), %r10
movq 0x18(%rsp), %r11
testb %r12b, %r12b
je 0x6ea1
movq 0x10(%rsp), %rax
movq 0x50(%rax), %rdi
callq 0x576a
testq %rax, %rax
je 0x6e6d
movq $0x0, 0x408(%rax)
movq $0x0, 0x400(%rax)
movq %rax, 0x8(%r14)
testb $0x1f, %bl
movq 0x10(%rsp), %r12
movq 0x20(%rsp), %r10
movq 0x18(%rsp), %r11
jne 0x6e36
cmpq $0x0, 0x8(%rsp)
je 0x6e4b
movq 0x40(%r12), %rcx
testq %rcx, %rcx
je 0x710f
movq %rax, 0x400(%rcx)
movq %rax, 0x40(%r12)
movq 0x8(%rsp), %rcx
testq %rcx, %rcx
cmoveq %rax, %rcx
movq %rcx, 0x8(%rsp)
movb $0x1, %cl
movq %rax, 0x30(%rsp)
jmp 0x6fb9
testb %r12b, %r12b
movq 0x20(%rsp), %r10
movq 0x18(%rsp), %r11
je 0x6ea1
movq 0x10(%rsp), %rax
movq 0x60(%rax), %rax
movq 0x8(%rax), %rcx
decq %rcx
movq (%rax), %rdx
decq %rdx
andq %rcx, %rdx
movq %rdx, 0x8(%rax)
movq $0x0, 0x8(%r14)
movq 0x40(%rsp), %rbp
movq %r10, %rax
movq 0x8(%rsp), %rdx
movq %rdx, %rcx
testq %rdx, %rdx
movq 0x10(%rsp), %r12
je 0x6f4c
movq 0x60(%r12), %rsi
movq 0x8(%rsi), %rdi
movq 0x18(%rsi), %rdx
movq (%rdx,%rdi,8), %r8
movq (%r8), %r8
cmpq $0x1, %r8
je 0x7310
movq %rax, %r9
subq %r8, %r9
shrq $0x5, %r9
addq %rdi, %r9
movq (%rsi), %rsi
decq %rsi
andq %r9, %rsi
movq (%rdx,%rsi,8), %rdx
movq (%rdx), %rsi
cmpq %rsi, %rax
jne 0x72f1
movq 0x8(%rdx), %rsi
testq %rsi, %rsi
je 0x72f1
movq $0x0, 0x8(%rdx)
movq 0x60(%r12), %rdx
movq 0x8(%rdx), %rsi
decq %rsi
movq (%rdx), %rdi
decq %rdi
andq %rsi, %rdi
movq %rdi, 0x8(%rdx)
movq 0x400(%rcx), %rcx
addq $0x20, %rax
testq %rcx, %rcx
jne 0x6ebf
addq $-0x20, %rax
movq %rax, %rbp
cmpq $0x0, 0x8(%rsp)
je 0x6fad
movq 0x50(%r12), %rcx
movq 0x8(%rsp), %rdx
movq %rdx, %rsi
movq 0x400(%rdx), %rdx
movl $0x80000000, %eax       # imm = 0x80000000
lock
xaddl %eax, 0x430(%rsi)
testl %eax, %eax
jne 0x6fa8
movq 0x28(%rcx), %rax
movq %rax, 0x438(%rsi)
movl $0x1, 0x430(%rsi)
lock
cmpxchgq %rsi, 0x28(%rcx)
je 0x6fa8
movl $0x7fffffff, %edi       # imm = 0x7FFFFFFF
lock
xaddl %edi, 0x430(%rsi)
cmpl $0x1, %edi
je 0x6f7d
testq %rdx, %rdx
jne 0x6f5e
movq 0x28(%rsp), %rax
movq %rax, 0x40(%r12)
xorl %ecx, %ecx
testb %cl, %cl
je 0x70c0
movq %rbp, %rax
addq $-0x20, %r13
jne 0x6d14
jmp 0x6fde
movq $0x0, 0x8(%rsp)
movq %rcx, 0x30(%rsp)
movq 0x28(%rsp), %rax
movq %rax, 0x40(%r12)
movq 0x38(%rsp), %rsi
testq %rsi, %rsi
movq 0x8(%rsp), %rcx
je 0x7007
movl %ebx, %eax
andl $0x1f, %eax
jne 0x7007
testq %rcx, %rcx
je 0x712e
testb $0x1f, %bl
movabsq $-0x8000000000000000, %rdx # imm = 0x8000000000000000
jne 0x7020
testq %rcx, %rcx
je 0x7020
movq %rcx, 0x40(%r12)
addq %rbx, %rsi
movq %rbx, %r13
movq 0x30(%rsp), %rdi
movq %rsi, 0x38(%rsp)
movq %r13, %r14
andq $-0x20, %r14
addq $0x20, %r14
movq %rsi, %rax
subq %r14, %rax
cmpq %rdx, %rax
cmovaq %rsi, %r14
cmpq %r14, %r13
je 0x7091
movl $0x20, %ebp
subq %r13, %rbp
movl %r13d, %edi
andl $0x1f, %edi
shll $0x5, %edi
addq 0x40(%r12), %rdi
movq %r15, %rsi
callq 0x734a
incq %r13
addq $0x20, %r15
decq %rbp
cmpq %r13, %r14
jne 0x7055
movq %r14, %r13
movabsq $-0x8000000000000000, %rdx # imm = 0x8000000000000000
movq 0x38(%rsp), %rsi
movq 0x30(%rsp), %rdi
movq 0x40(%r12), %rax
cmpq %rdi, %rax
je 0x70a9
movq 0x400(%rax), %rcx
movq %rcx, 0x40(%r12)
jmp 0x70ae
cmpq %rsi, %r13
jne 0x70f0
cmpq %rdi, %rax
jne 0x7030
movq %rsi, 0x20(%r12)
movb $0x1, %al
jmp 0x70c2
xorl %eax, %eax
addq $0x48, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0x150b(%rip), %rdi      # 0x85e3
leaq 0xfb8(%rip), %rsi       # 0x8097
leaq 0x1e7c(%rip), %rcx      # 0x8f62
movl $0xa53, %edx            # imm = 0xA53
callq 0x3160
leaq 0x2018(%rip), %rdi      # 0x910f
leaq 0xf99(%rip), %rsi       # 0x8097
leaq 0x1e5d(%rip), %rcx      # 0x8f62
movl $0xac0, %edx            # imm = 0xAC0
callq 0x3160
leaq 0x1f71(%rip), %rdi      # 0x9087
leaq 0xf7a(%rip), %rsi       # 0x8097
leaq 0x1e3e(%rip), %rcx      # 0x8f62
movl $0xa76, %edx            # imm = 0xA76
callq 0x3160
leaq 0x1f6d(%rip), %rdi      # 0x90a2
leaq 0xf5b(%rip), %rsi       # 0x8097
leaq 0x1e1f(%rip), %rcx      # 0x8f62
movl $0xa83, %edx            # imm = 0xA83
callq 0x3160
leaq 0x15de(%rip), %rdi      # 0x8732
leaq 0xf3c(%rip), %rsi       # 0x8097
leaq 0x1614(%rip), %rcx      # 0x8776
movl $0xb60, %edx            # imm = 0xB60
callq 0x3160
movq %rax, %rdi
callq 0x30e0
testb $0x1f, %bl
movq 0x40(%r12), %r14
movq 0x28(%rsp), %r15
cmoveq 0x8(%rsp), %r15
negq %rbp
movq %rbx, %r12
andq $-0x20, %r12
movq %rbp, %rax
subq %r12, %rax
addq $0x20, %r12
movabsq $-0x8000000000000000, %rcx # imm = 0x8000000000000000
cmpq %rcx, %rax
cmovaq %r13, %r12
cmpq %r12, %rbx
je 0x71db
movl %ebx, %edi
andl $0x1f, %edi
shll $0x5, %edi
movq 0x10(%r15,%rdi), %rax
testq %rax, %rax
je 0x71d0
addq %r15, %rdi
movq %rdi, %rsi
movl $0x3, %edx
callq *%rax
incq %rbx
cmpq %rbx, %r12
jne 0x71b1
movq %r12, %rbx
cmpq %r14, %r15
je 0x71e9
movq 0x400(%r15), %r15
jmp 0x718a
movq 0x8(%rsp), %rax
testq %rax, %rax
jne 0x7206
movq 0x10(%rsp), %rax
movq 0x28(%rsp), %rcx
movq %rcx, 0x40(%rax)
callq 0x32f0
movq 0x40(%rsp), %r10
addq $0x20, %r10
movq 0x10(%rsp), %r9
movq 0x60(%r9), %rdx
movq 0x8(%rdx), %rsi
movq 0x18(%rdx), %rcx
movq (%rcx,%rsi,8), %rdi
movq (%rdi), %rdi
cmpq $0x1, %rdi
je 0x7310
movq %r10, %r8
subq %rdi, %r8
shrq $0x5, %r8
addq %rsi, %r8
movq (%rdx), %rdx
decq %rdx
andq %r8, %rdx
movq (%rcx,%rdx,8), %rcx
movq (%rcx), %rdx
cmpq %rdx, %r10
jne 0x72f1
movq 0x8(%rcx), %rdx
testq %rdx, %rdx
je 0x72f1
movq $0x0, 0x8(%rcx)
movq 0x60(%r9), %rcx
movq 0x8(%rcx), %rdx
decq %rdx
movq (%rcx), %rsi
decq %rsi
andq %rdx, %rsi
movq %rsi, 0x8(%rcx)
movq 0x400(%rax), %rax
addq $0x20, %r10
testq %rax, %rax
jne 0x7214
movq 0x50(%r9), %rcx
movq 0x8(%rsp), %rdi
movq %rdi, %rdx
movq 0x400(%rdi), %rdi
movl $0x80000000, %eax       # imm = 0x80000000
lock
xaddl %eax, 0x430(%rdx)
testl %eax, %eax
jne 0x72e7
movq 0x28(%rcx), %rax
movq %rax, 0x438(%rdx)
movl $0x1, 0x430(%rdx)
lock
cmpxchgq %rdx, 0x28(%rcx)
je 0x72e7
movl $0x7fffffff, %esi       # imm = 0x7FFFFFFF
lock
xaddl %esi, 0x430(%rdx)
cmpl $0x1, %esi
je 0x72bc
testq %rdi, %rdi
jne 0x729d
jmp 0x71f3
leaq 0x1250(%rip), %rdi      # 0x8548
leaq 0xd98(%rip), %rsi       # 0x8097
leaq 0x1160(%rip), %rcx      # 0x8466
movl $0xb81, %edx            # imm = 0xB81
callq 0x3160
leaq 0x1130(%rip), %rdi      # 0x8447
leaq 0xd79(%rip), %rsi       # 0x8097
leaq 0x1141(%rip), %rcx      # 0x8466
movl $0xb7c, %edx            # imm = 0xB7C
callq 0x3160
movq %rax, %rbx
callq 0x3330
movq %rbx, %rdi
callq 0x3380
jmp 0x7341
movq %rax, %rdi
callq 0x3c7b
nop