// File: /workspace/github_cpp_makefile_star2_O2/kebwi[P]Trifid/src/SteerablePyramid.cpp
// Function: SteerablePyramid::getFilterFTIndex()
int SteerablePyramid::getFilterFTIndex()
{
	assert(skFilterDims[0] > 0);
	
	//Search the currently defined filter FTs for one with the appropriate dimensions.
	//If one is found, return its index.
	for (int i = 0; i < skFiltersFTs.size(); i++)
		if (skFiltersFTs[i].width_ == width_ && skFiltersFTs[i].height_ == height_)
			return i;
	
	//No filter FT with the appropriate dimensions was found, so add a new one and return its index.
	FilterFT filterFT;
	skFiltersFTs.push_back(filterFT);
	skFiltersFTs.back().resize(width_, height_);
	
	Float_t *shiftBuffer = new Float_t[width_ * height_];
	for (int i = 0; i < 7; i++)
		for (int lvl = 0 ; lvl < numLevels_; lvl++)
		{	
			int filterDim = skFilterDims[i];
			
			int horDim = width_ / pow(2, lvl);
			int verDim = height_ / pow(2, lvl);
			assert(horDim >= filterDim && verDim >= filterDim);
			
			memset(shiftBuffer, 0, horDim * verDim * sizeof(Float_t));
			
			int xOffset = (horDim - filterDim) / 2;
			int yOffset = (verDim - filterDim) / 2;
			
			//By default, an embedded odd-length signal will be positioned such that the center pixel
			//resides at lower right, but I prefer that it be at upper left, so shift it by one.
			assert(filterDim % 2 == 1);	//All the filters should have odd dimensions
			if (filterDim % 2 == 1)
			{
				xOffset++;
				yOffset++;
			}
			
			//Copy the filter to the temp buffer 
			for (int y = 0; y < filterDim; y++)
				for (int x = 0; x < filterDim; x++)
					shiftBuffer[(y + yOffset) * horDim + (x + xOffset)] =
						skFilters[i][y * filterDim + x];
			
			//Shift (with wrap) the center to the corners
			for (int y = 0; y < verDim; y++)
				for (int x = 0; x < horDim; x++)
					skFiltersFTs.back().filtersFTs[i][lvl][y * horDim + x] =
						shiftBuffer[((y + verDim / 2) % verDim) * horDim + (x + horDim / 2) % horDim];
			
			//Do the Fourier analysis
			assert(doFourierAnalysis(skFiltersFTs.back().filtersFTs[i][lvl],
									skFiltersFTs.back().filtersFTs[i][lvl], horDim, verDim));
			
			//Copy the inverse filter to the temp buffer 
			for (int y = 0; y < filterDim; y++)
				for (int x = 0; x < filterDim; x++)
					shiftBuffer[(y + yOffset) * horDim + (x + xOffset)] =
						skFiltersInv[i][y * filterDim + x];
			
			//Shift (with wrap) the center to the corners
			for (int y = 0; y < verDim; y++)
				for (int x = 0; x < horDim; x++)
					skFiltersFTs.back().filtersInvFTs[i][lvl][y * horDim + x] =
						shiftBuffer[((y + verDim / 2) % verDim) * horDim + (x + horDim / 2) % horDim];
			
			//Do the Fourier analysis
			assert(doFourierAnalysis(skFiltersFTs.back().filtersInvFTs[i][lvl],
									skFiltersFTs.back().filtersInvFTs[i][lvl], horDim, verDim));
		}
	delete [] shiftBuffer;
	
	return skFiltersFTs.size() - 1;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x1a8, %rsp            # imm = 0x1A8
cmpl $0x0, 0x1cbf8(%rip)     # 0x32af0
jle 0x16368
movq %rdi, %r15
movq 0x1cbb8(%rip), %rax     # 0x32ac0
movq 0x1cba9(%rip), %rcx     # 0x32ab8
subq %rcx, %rax
movl $0x158, %esi            # imm = 0x158
cqto
idivq %rsi
movl 0x30(%rdi), %edx
movl 0x34(%rdi), %esi
addq $0x4, %rcx
xorl %r14d, %r14d
cmpq %r14, %rax
je 0x15f47
cmpl %edx, -0x4(%rcx)
jne 0x15f3b
cmpl %esi, (%rcx)
je 0x162d7
incq %r14
addq $0x158, %rcx            # imm = 0x158
jmp 0x15f29
leaq 0x50(%rsp), %r14
movl $0x158, %edx            # imm = 0x158
movq %r14, %rdi
xorl %esi, %esi
callq 0x3170
leaq 0x1cb56(%rip), %rdi     # 0x32ab8
movq %r14, %rsi
callq 0x1a812
movq 0x1cb4f(%rip), %rdi     # 0x32ac0
movq 0x30(%r15), %rax
movq %rax, -0x158(%rdi)
addq $-0x158, %rdi           # imm = 0xFEA8
callq 0x1aa88
movslq 0x30(%r15), %rax
movslq 0x34(%r15), %rcx
imulq %rax, %rcx
movq %rcx, %rax
shlq $0x3, %rax
testl %ecx, %ecx
pushq $-0x1
popq %rdi
cmovnsq %rax, %rdi
callq 0x3030
movq %rax, %r14
xorl %ebx, %ebx
movq %r15, 0x30(%rsp)
cmpq $0x7, %rbx
je 0x162a7
xorl %r12d, %r12d
movslq 0x38(%r15), %rax
cmpq %rax, %r12
jge 0x1629f
leaq 0x1cb1c(%rip), %rax     # 0x32af0
movl (%rax,%rbx,4), %ebp
cvtsi2sd %r12d, %xmm0
movsd %xmm0, (%rsp)
movss 0x30(%r15), %xmm1
movaps %xmm1, 0x10(%rsp)
callq 0x3280
movapd %xmm0, 0x20(%rsp)
movups 0x34(%r15), %xmm0
unpcklps 0x10(%rsp), %xmm0       # xmm0 = xmm0[0],mem[0],xmm0[1],mem[1]
cvtdq2pd %xmm0, %xmm0
movaps %xmm0, 0x10(%rsp)
movsd (%rsp), %xmm0
callq 0x3280
unpcklpd 0x20(%rsp), %xmm0       # xmm0 = xmm0[0],mem[0]
movapd 0x10(%rsp), %xmm1
divpd %xmm0, %xmm1
cvttpd2dq %xmm1, %xmm0
movd %ebp, %xmm1
pshufd $0x50, %xmm0, %xmm2     # xmm2 = xmm0[0,0,1,1]
pshufd $0x0, %xmm1, %xmm1      # xmm1 = xmm1[0,0,0,0]
pcmpgtd %xmm2, %xmm1
movmskpd %xmm1, %eax
xorl $0x3, %eax
cmpl $0x3, %eax
jne 0x162ec
movl %ebp, %r13d
movd %xmm0, %ebp
pshufd $0x55, %xmm0, %xmm0     # xmm0 = xmm0[1,1,1,1]
movd %xmm0, %r15d
movl %ebp, %eax
imull %r15d, %eax
movslq %eax, %rdx
shlq $0x3, %rdx
movq %r14, %rdi
xorl %esi, %esi
callq 0x3170
movq %r13, %rdi
movl %edi, %eax
andl $0x80000001, %eax       # imm = 0x80000001
cmpl $0x1, %eax
jne 0x1630b
movl %ebp, %eax
subl %edi, %eax
cltd
pushq $0x2
popq %rsi
idivl %esi
movl %eax, %ecx
movl %r15d, %eax
subl %edi, %eax
cltd
idivl %esi
movslq %r15d, %r11
leaq (,%rdi,8), %r13
incl %ecx
imull %r15d, %ecx
addl %ecx, %eax
incl %eax
movl %eax, 0xc(%rsp)
xorl %ecx, %ecx
xorl %edx, %edx
leaq 0x1ca53(%rip), %r10     # 0x32b10
movq %rdi, (%rsp)
cmpq %rdi, %rdx
je 0x160fb
movl %eax, %esi
movq %rcx, %r8
subq $0x1, %rdi
jb 0x160ec
movq (%r10,%rbx,8), %r9
movq (%r9,%r8), %xmm0
movslq %esi, %rsi
movq %xmm0, (%r14,%rsi,8)
addq $0x8, %r8
incl %esi
jmp 0x160cb
incq %rdx
addq %r13, %rcx
addl %r15d, %eax
movq (%rsp), %rdi
jmp 0x160c1
movq %r13, 0x40(%rsp)
movl %ebp, %eax
cltd
pushq $0x2
popq %rcx
idivl %ecx
movq %rax, 0x10(%rsp)
movl %r15d, %eax
cltd
idivl %ecx
movl %eax, %r13d
movl %ebp, %eax
movq %rax, 0x20(%rsp)
shlq $0x3, %r11
xorl %edi, %edi
xorl %r8d, %r8d
imulq $0x18, %rbx, %rcx
movq 0x1c98f(%rip), %rax     # 0x32ac0
leaq (%rax,%rcx), %r9
addq $-0x150, %r9            # imm = 0xFEB0
cmpq 0x20(%rsp), %r8
je 0x1618f
movq 0x10(%rsp), %rax
leal (%rax,%r8), %ecx
xorl %r10d, %r10d
cmpq %r10, %r15
je 0x16187
movl %ecx, %eax
cltd
idivl %ebp
movl %edx, %esi
imull %r15d, %esi
leal (%r10,%r13), %eax
cltd
idivl %r15d
addl %esi, %edx
movslq %edx, %rax
movq (%r14,%rax,8), %xmm0
movq (%r9), %rax
movq (%rax,%r12,8), %rax
addq %rdi, %rax
movq %xmm0, (%rax,%r10,8)
incq %r10
jmp 0x1614f
incq %r8
addq %r11, %rdi
jmp 0x16126
movq %rcx, 0x48(%rsp)
movq %r11, 0x38(%rsp)
movq (%r9), %rax
movq (%rax,%r12,8), %rdi
movq %rdi, %rsi
movl %r15d, %edx
movl %ebp, %ecx
callq 0x140ee
testb %al, %al
je 0x16349
xorl %eax, %eax
xorl %ecx, %ecx
leaq 0x1c990(%rip), %r9      # 0x32b50
movq 0x38(%rsp), %r11
movl 0xc(%rsp), %r10d
movq (%rsp), %rsi
cmpq %rsi, %rcx
je 0x16207
movl %r10d, %edx
movq %rax, %rdi
subq $0x1, %rsi
jb 0x161fa
movq (%r9,%rbx,8), %r8
movq (%r8,%rdi), %xmm0
movslq %edx, %rdx
movq %xmm0, (%r14,%rdx,8)
addq $0x8, %rdi
incl %edx
jmp 0x161d9
incq %rcx
addq 0x40(%rsp), %rax
addl %r15d, %r10d
jmp 0x161ca
xorl %edi, %edi
xorl %r8d, %r8d
movq 0x1c8ad(%rip), %rax     # 0x32ac0
movq 0x48(%rsp), %rcx
leaq (%rax,%rcx), %r9
addq $-0xa8, %r9
cmpq 0x20(%rsp), %r8
je 0x16276
movq 0x10(%rsp), %rax
leal (%rax,%r8), %ecx
xorl %r10d, %r10d
cmpq %r10, %r15
je 0x1626e
movl %ecx, %eax
cltd
idivl %ebp
movl %edx, %esi
imull %r15d, %esi
leal (%r10,%r13), %eax
cltd
idivl %r15d
addl %esi, %edx
movslq %edx, %rax
movq (%r14,%rax,8), %xmm0
movq (%r9), %rax
movq (%rax,%r12,8), %rax
addq %rdi, %rax
movq %xmm0, (%rax,%r10,8)
incq %r10
jmp 0x16236
incq %r8
addq %r11, %rdi
jmp 0x1620c
movq (%r9), %rax
movq (%rax,%r12,8), %rdi
movq %rdi, %rsi
movl %r15d, %edx
movl %ebp, %ecx
callq 0x140ee
incq %r12
testb %al, %al
movq 0x30(%rsp), %r15
jne 0x15fc0
jmp 0x1632a
incq %rbx
jmp 0x15fb3
movq %r14, %rdi
callq 0x3380
movq 0x1c80a(%rip), %rax     # 0x32ac0
subq 0x1c7fb(%rip), %rax     # 0x32ab8
movl $0x158, %ecx            # imm = 0x158
cqto
idivq %rcx
movq %rax, %r14
decl %r14d
leaq 0x50(%rsp), %rdi
callq 0x1a842
movl %r14d, %eax
addq $0x1a8, %rsp            # imm = 0x1A8
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
leaq 0xf095(%rip), %rdi      # 0x25388
leaq 0xefc8(%rip), %rsi      # 0x252c2
leaq 0xf05e(%rip), %rcx      # 0x2535f
movl $0x166, %edx            # imm = 0x166
callq 0x31a0
leaq 0xf017(%rip), %rdi      # 0x25329
leaq 0xefa9(%rip), %rsi      # 0x252c2
leaq 0xf03f(%rip), %rcx      # 0x2535f
movl $0x16f, %edx            # imm = 0x16F
callq 0x31a0
leaq 0xf0f4(%rip), %rdi      # 0x25425
leaq 0xef8a(%rip), %rsi      # 0x252c2
leaq 0xf020(%rip), %rcx      # 0x2535f
movl $0x194, %edx            # imm = 0x194
callq 0x31a0
leaq 0xf063(%rip), %rdi      # 0x253b3
leaq 0xef6b(%rip), %rsi      # 0x252c2
leaq 0xf001(%rip), %rcx      # 0x2535f
movl $0x184, %edx            # imm = 0x184
callq 0x31a0
leaq 0xefdc(%rip), %rdi      # 0x2534b
leaq 0xef4c(%rip), %rsi      # 0x252c2
leaq 0xefe2(%rip), %rcx      # 0x2535f
movl $0x151, %edx            # imm = 0x151
callq 0x31a0
jmp 0x1638b
jmp 0x1638b
movq %rax, %rbx
leaq 0x50(%rsp), %rdi
callq 0x1a842
movq %rbx, %rdi
callq 0x34d0