// File: wichtounet[P]articles/plf_colony_alpha/plf_timsort.h
// Function: long plf::TimSort<Trivial<8>**, plf::colony<Trivial<8>, std::allocator<Trivial<8>>, unsigned short>::sort_dereferencer<plf::colony<Trivial<8>, std::allocator<Trivial<8>>, unsigned short>::less>>::gallopLeft<Trivial<8>**>(Trivial<8>*&, Trivial<8>**, long, long)
diff_t gallopLeft(ref_t key, Iter const base, diff_t const len, diff_t const hint)
	{
		assert(len > 0 && hint >= 0 && hint < len);

		diff_t lastOfs = 0;
		diff_t ofs = 1;

		if (comp_.gt(key, *(base + hint)))
		{
			diff_t const maxOfs = len - hint;

			while (ofs < maxOfs && comp_.gt(key, *(base + (hint + ofs))))
			{
				lastOfs = ofs;
				ofs = (ofs << 1) + 1;

				if (ofs <= 0)   // int overflow
				{
					ofs = maxOfs;
				}
			}

			if (ofs > maxOfs)
			{
				ofs = maxOfs;
			}

			lastOfs += hint;
			ofs += hint;
		}
		else
		{
			diff_t const maxOfs = hint + 1;

			while (ofs < maxOfs && comp_.le(key, *(base + (hint - ofs))))
			{
				lastOfs = ofs;
				ofs = (ofs << 1) + 1;

				if (ofs <= 0)
				{
					ofs = maxOfs;
				}
			}

			if (ofs > maxOfs)
			{
				ofs = maxOfs;
			}

			diff_t const tmp = lastOfs;
			lastOfs = hint - ofs;
			ofs = hint - tmp;
		}
		assert(-1 <= lastOfs && lastOfs < ofs && ofs <= len);

		return std::lower_bound(base + (lastOfs + 1), base + ofs, key, comp_.less_function()) - base;
	}

// Assembly:
subq $0x88, %rsp
movq %rdi, 0x80(%rsp)
movq %rsi, 0x78(%rsp)
movq %rdx, 0x70(%rsp)
movq %rcx, 0x68(%rsp)
movq %r8, 0x60(%rsp)
movq 0x80(%rsp), %rdi
movq %rdi, 0x28(%rsp)
movq $0x0, 0x58(%rsp)
movq $0x1, 0x50(%rsp)
movq 0x78(%rsp), %rsi
movq 0x70(%rsp), %rdx
movq 0x60(%rsp), %rax
shlq $0x3, %rax
addq %rax, %rdx
callq 0xe8150
testb $0x1, %al
jne 0xe7126
jmp 0xe71e2
movq 0x68(%rsp), %rax
subq 0x60(%rsp), %rax
movq %rax, 0x48(%rsp)
movq 0x50(%rsp), %rcx
xorl %eax, %eax
cmpq 0x48(%rsp), %rcx
movb %al, 0x27(%rsp)
jge 0xe7170
movq 0x28(%rsp), %rdi
movq 0x78(%rsp), %rsi
movq 0x70(%rsp), %rdx
movq 0x60(%rsp), %rax
addq 0x50(%rsp), %rax
shlq $0x3, %rax
addq %rax, %rdx
callq 0xe8150
movb %al, 0x27(%rsp)
movb 0x27(%rsp), %al
testb $0x1, %al
jne 0xe717a
jmp 0xe71a9
movq 0x50(%rsp), %rax
movq %rax, 0x58(%rsp)
movq 0x50(%rsp), %rax
shlq %rax
addq $0x1, %rax
movq %rax, 0x50(%rsp)
cmpq $0x0, 0x50(%rsp)
jg 0xe71a7
movq 0x48(%rsp), %rax
movq %rax, 0x50(%rsp)
jmp 0xe7135
movq 0x50(%rsp), %rax
cmpq 0x48(%rsp), %rax
jle 0xe71bf
movq 0x48(%rsp), %rax
movq %rax, 0x50(%rsp)
movq 0x60(%rsp), %rax
addq 0x58(%rsp), %rax
movq %rax, 0x58(%rsp)
movq 0x60(%rsp), %rax
addq 0x50(%rsp), %rax
movq %rax, 0x50(%rsp)
jmp 0xe72a2
movq 0x60(%rsp), %rax
addq $0x1, %rax
movq %rax, 0x40(%rsp)
movq 0x50(%rsp), %rcx
xorl %eax, %eax
cmpq 0x40(%rsp), %rcx
movb %al, 0x26(%rsp)
jge 0xe722b
movq 0x28(%rsp), %rdi
movq 0x78(%rsp), %rsi
movq 0x70(%rsp), %rdx
movq 0x60(%rsp), %rax
subq 0x50(%rsp), %rax
shlq $0x3, %rax
addq %rax, %rdx
callq 0xe81c0
movb %al, 0x26(%rsp)
movb 0x26(%rsp), %al
testb $0x1, %al
jne 0xe7235
jmp 0xe7264
movq 0x50(%rsp), %rax
movq %rax, 0x58(%rsp)
movq 0x50(%rsp), %rax
shlq %rax
addq $0x1, %rax
movq %rax, 0x50(%rsp)
cmpq $0x0, 0x50(%rsp)
jg 0xe7262
movq 0x40(%rsp), %rax
movq %rax, 0x50(%rsp)
jmp 0xe71f0
movq 0x50(%rsp), %rax
cmpq 0x40(%rsp), %rax
jle 0xe727a
movq 0x40(%rsp), %rax
movq %rax, 0x50(%rsp)
movq 0x58(%rsp), %rax
movq %rax, 0x38(%rsp)
movq 0x60(%rsp), %rax
subq 0x50(%rsp), %rax
movq %rax, 0x58(%rsp)
movq 0x60(%rsp), %rax
subq 0x38(%rsp), %rax
movq %rax, 0x50(%rsp)
movq 0x28(%rsp), %rdi
movq 0x70(%rsp), %rax
movq 0x58(%rsp), %rcx
addq $0x1, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movq %rax, 0x8(%rsp)
movq 0x70(%rsp), %rax
movq 0x50(%rsp), %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movq %rax, 0x10(%rsp)
movq 0x78(%rsp), %rax
movq %rax, 0x18(%rsp)
callq 0xe5fd0
movq 0x8(%rsp), %rdi
movq 0x10(%rsp), %rsi
movq 0x18(%rsp), %rdx
movb (%rax), %al
movb %al, 0x37(%rsp)
callq 0xe8230
movq 0x70(%rsp), %rcx
subq %rcx, %rax
sarq $0x3, %rax
addq $0x88, %rsp
retq
nopw %cs:(%rax,%rax)
nop