// File: /workspace/github_cpp_makefile_star2_O1/splatlab[P]debgr/threadsafe-gqf/gqf.c
// Function: run_end(quotient_filter const*, unsigned long)
static inline uint64_t run_end(const QF *qf, uint64_t hash_bucket_index)
{
	uint64_t bucket_block_index       = hash_bucket_index / SLOTS_PER_BLOCK;
	uint64_t bucket_intrablock_offset = hash_bucket_index % SLOTS_PER_BLOCK;
	uint64_t bucket_blocks_offset = block_offset(qf, bucket_block_index);

	// uint64_t bucket_intrablock_rank   = bitrankv(get_block(qf, bucket_block_index)->occupieds, METADATA_WORDS_PER_BLOCK, bucket_intrablock_offset);
	uint64_t bucket_intrablock_rank   = bitrank(get_block(qf,
																												bucket_block_index)->occupieds[0],
																							bucket_intrablock_offset);

	if (bucket_intrablock_rank == 0) {
		if (bucket_blocks_offset <= bucket_intrablock_offset)
			return hash_bucket_index;
		else
			return SLOTS_PER_BLOCK * bucket_block_index + bucket_blocks_offset - 1;
	}

	/* FIXME: Should handle offset overflow  --- Ah screw it, just use 16-bit offset.  That'll never overflow.  */
	uint64_t runend_block_index  = bucket_block_index + bucket_blocks_offset /
		SLOTS_PER_BLOCK;
	uint64_t runend_ignore_bits  = bucket_blocks_offset % SLOTS_PER_BLOCK;
	uint64_t runend_rank         = bucket_intrablock_rank - 1;
	// uint64_t runend_block_offset = bitselectv(get_block(qf, runend_block_index)->runends, METADATA_WORDS_PER_BLOCK, runend_ignore_bits, runend_rank);
	uint64_t runend_block_offset = bitselectv(get_block(qf,
																											runend_block_index)->runends[0],
																						runend_ignore_bits, runend_rank);
	if (runend_block_offset == SLOTS_PER_BLOCK) {
		if (bucket_blocks_offset == 0 && bucket_intrablock_rank == 0) {
			/* The block begins in empty space, and this bucket is in that region of empty space */
			return hash_bucket_index;
		} else {
			do {
				// runend_rank        -= popcntv(get_block(qf, runend_block_index)->runends, METADATA_WORDS_PER_BLOCK, runend_ignore_bits);
				runend_rank        -= popcntv(get_block(qf,
																								runend_block_index)->runends[0],
																			runend_ignore_bits);
				runend_block_index++;
				runend_ignore_bits  = 0;
				// runend_block_offset = bitselectv(get_block(qf, runend_block_index)->runends, METADATA_WORDS_PER_BLOCK, runend_ignore_bits, runend_rank);
				runend_block_offset = bitselectv(get_block(qf,
																									 runend_block_index)->runends[0],
																				 runend_ignore_bits, runend_rank);
			} while (runend_block_offset == SLOTS_PER_BLOCK);
		}
	}

	uint64_t runend_index = SLOTS_PER_BLOCK * runend_block_index + runend_block_offset;
	if (runend_index < hash_bucket_index)
		return hash_bucket_index;
	else
		return runend_index;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
movq %rsi, %rbp
shrq $0x6, %rbp
movl %esi, %ecx
andl $0x3f, %ecx
movq 0x8(%rdi), %rax
movq 0x10(%rdi), %rdi
movabsq $0x3ffffffffffffff, %rdx # imm = 0x3FFFFFFFFFFFFFF
andq 0x38(%rax), %rdx
leaq 0x11(,%rdx,8), %r8
movq %r8, %r9
imulq %rbp, %r9
movzbl (%rdi,%r9), %edx
movl $0x2, %eax
shlq %cl, %rax
decq %rax
andq 0x1(%rdi,%r9), %rax
popcntq %rax, %rax
testl %eax, %eax
je 0x126b1
movq %rsi, -0x8(%rsp)
movabsq $-0x7f7f7f7f7f7f7f80, %r10 # imm = 0x8080808080808080
movabsq $0x3333333333333333, %rbx # imm = 0x3333333333333333
movslq %eax, %r12
movl %edx, %r9d
shrl $0x6, %r9d
leaq (%r9,%rbp), %rax
decq %r12
movq %rax, %r13
imulq %r8, %r13
movq 0x9(%rdi,%r13), %r11
movl %edx, %ecx
shrq %cl, %r11
shlq %cl, %r11
movq %r11, %rcx
popcntq %rcx, %rcx
movl $0x40, %r15d
cmpl %r12d, %ecx
jle 0x1257b
movq %r11, %rcx
shrq %rcx
movabsq $0x5555555555555555, %rsi # imm = 0x5555555555555555
andq %rsi, %rcx
movq %r11, %rsi
subq %rcx, %rsi
movq %rsi, %rcx
andq %rbx, %rcx
shrq $0x2, %rsi
andq %rbx, %rsi
addq %rcx, %rsi
movq %rsi, %r14
shrq $0x4, %r14
addq %rsi, %r14
movabsq $0xf0f0f0f0f0f0f0f, %rcx # imm = 0xF0F0F0F0F0F0F0F
andq %rcx, %r14
movq %r14, %rcx
movabsq $-0x101010101010101, %rsi # imm = 0xFEFEFEFEFEFEFEFF
imulq %rsi, %rcx
movslq %r12d, %r15
movabsq $0x101010101010100, %rsi # imm = 0x101010101010100
incq %rsi
imulq %r15, %rsi
orq %r10, %rsi
addq %rcx, %rsi
andq %r10, %rsi
popcntq %rsi, %rsi
shll $0x3, %esi
movslq %esi, %rcx
movabsq $0x101010101010100, %rsi # imm = 0x101010101010100
imulq %rsi, %r14
shrq %cl, %r14
movl $0xff, %esi
shrq %cl, %r11
andq %rsi, %r14
subq %r14, %r15
andq %rsi, %r11
shlq $0x8, %r15
orq %r11, %r15
leaq 0x25cd(%rip), %rsi      # 0x14b40
movzbl (%rsi,%r15), %r15d
addq %rcx, %r15
cmpq $0x40, %r15
jne 0x1269c
addq $0x9, %rdi
andl $0x3f, %edx
addq %r9, %rbp
incq %rbp
imulq %r8, %rbp
movabsq $0x101010101010100, %rcx # imm = 0x101010101010100
leaq 0x1(%rcx), %r9
movl $0xff, %r11d
movq (%rdi,%r13), %r14
testl %edx, %edx
je 0x125c1
movl %edx, %ecx
shrq %cl, %r14
shlq %cl, %r14
popcntq %r14, %r14
jmp 0x125c6
popcntq %r14, %r14
movslq %r14d, %rcx
subq %rcx, %r12
movq (%rdi,%rbp), %rdx
movq %rdx, %rcx
popcntq %rcx, %rcx
movl $0x40, %r15d
cmpl %r12d, %ecx
jle 0x1268a
movq %rdx, %rcx
shrq %rcx
movabsq $0x5555555555555555, %rsi # imm = 0x5555555555555555
andq %rsi, %rcx
movq %rdx, %r15
subq %rcx, %r15
movq %r15, %rcx
andq %rbx, %rcx
shrq $0x2, %r15
andq %rbx, %r15
addq %rcx, %r15
movq %r15, %r14
shrq $0x4, %r14
addq %r15, %r14
movabsq $0xf0f0f0f0f0f0f0f, %rcx # imm = 0xF0F0F0F0F0F0F0F
andq %rcx, %r14
movq %r14, %rcx
movabsq $-0x101010101010101, %rsi # imm = 0xFEFEFEFEFEFEFEFF
imulq %rsi, %rcx
movslq %r12d, %rsi
movq %rsi, %r15
imulq %r9, %r15
orq %r10, %r15
addq %rcx, %r15
andq %r10, %r15
popcntq %r15, %r15
shll $0x3, %r15d
movslq %r15d, %rcx
movabsq $0x101010101010100, %r15 # imm = 0x101010101010100
imulq %r15, %r14
shrq %cl, %r14
andq %r11, %r14
subq %r14, %rsi
shrq %cl, %rdx
andq %r11, %rdx
shlq $0x8, %rsi
orq %rdx, %rsi
leaq 0x24be(%rip), %rdx      # 0x14b40
movzbl (%rdx,%rsi), %r15d
addq %rcx, %r15
addq %r8, %rdi
incq %rax
xorl %edx, %edx
cmpq $0x40, %r15
je 0x125aa
shlq $0x6, %rax
addq %r15, %rax
movq -0x8(%rsp), %rcx
cmpq %rcx, %rax
cmovbeq %rcx, %rax
jmp 0x126c2
cmpl %edx, %ecx
jae 0x126bf
andq $-0x40, %rsi
addq %rdx, %rsi
decq %rsi
movq %rsi, %rax
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq