// File: kebwi[P]Trifid/src/main.cpp
// Function: testPGMFourierAnalysis()
void testPGMFourierAnalysis()
{	
	ImageReal firstImagePowerSpectrum;
	
	//PGM
	for (int imageIdx = 0; imageIdx < sInputFilenames.size(); imageIdx++)
	{
		//Open pgm
		ImageReal grayImg;
		grayImg.readFile(sInputFilenames[imageIdx]);
		int width = grayImg.width(), height = grayImg.height();
		int halfWidth = width / 2, halfHeight = height / 2;
		
		ImageReal fourierTransform;
		bool err = doFourierAnalysis(grayImg, fourierTransform);
		
		//Make an image of the power spectrum
		ImageReal powerSpectrum;
		generatePowerSpectrum(fourierTransform, powerSpectrum, GT_LOG10, true);
		
		powerSpectrum.setFilename(grayImg.filename());
		powerSpectrum.appendFilename("_ps");
		powerSpectrum.writeFile(1);
		
		bool shiftCenter = false;
		/*
		//Make a 1D histogram of the power spectrum, binned by frequency
		myAssert(!shiftCenter);
		generatePowerSpectrum(fourierTransform, powerSpectrum, GT_NONE, shiftCenter);
		if (imageIdx == 0)
			firstImagePowerSpectrum = powerSpectrum;
		
		int numBins = sqrt(halfWidth * halfWidth + halfHeight * halfHeight);
		cout << "Num bins: " << numBins << endl;
		int numBinsScalar = 4;
		numBins /= numBinsScalar;
		numBins++;
		cout << "Num bins scaled: " << numBins << endl;
		
		Float_t *powerSpectrumHistrogram = new Float_t[numBins];
		memset(powerSpectrumHistrogram, 0, numBins * sizeof(Float_t));
		
		int *binCounts = new int[numBins];
		memset(binCounts, 0, numBins * sizeof(int));
		
		//This code only works if the power spectrum has NOT been center-shifted.
		for (int y = 0; y < height; y++)
		{
			int yCenter = (y <= height / 2) ? 0 : height;
			Float_t yDistSqr = pow((Float_t)y - (Float_t)yCenter, 2);
			for (int x = 0; x <= halfWidth; x++)	//Step one column past the center (Nyquist)
			{
				if (y == 0 && x == 0)
					continue;	//Skip the DC term
				
				Float_t xDistSqr = pow((Float_t)x, 2);
				int dcTermDistance = roundToNearestInt(sqrt(yDistSqr + xDistSqr), 0, 0);
				dcTermDistance--;	//Since we skipped the DC term
				dcTermDistance /= numBinsScalar;
				myAssert(dcTermDistance >= 0 && dcTermDistance < numBins);
				
				powerSpectrumHistrogram[dcTermDistance] += powerSpectrum(x, y);
				binCounts[dcTermDistance]++;
			}
		}
		
		//Divide each bin by its number of contributing Fourier coefficients.
		//The result will be a histogram in which the value in each bin
		//represents the mean power at the frequency corresponding to that bin,
		//i.e., the mean power in a very thin annulus surrounding the DC term
		//in the power spectrum.
		int maxBinCount = 0;
		for (int i = 0; i < numBins; i++)
			if (binCounts[i] > maxBinCount)
				maxBinCount = binCounts[i];
		for (int i = 0; i < numBins; i++)
			powerSpectrumHistrogram[i] /= (Float_t)maxBinCount;
		
		string filename = sInputFilenames[imageIdx] + "_hist.txt";
		ofstream ofs;
		ofs.open(filename.c_str());
		myAssert(ofs);
		
		for (int i = 0; i < numBins; i++)
			ofs << i << '\t' << powerSpectrumHistrogram[i] << endl;
		
		ofs.close();
		
		delete [] powerSpectrumHistrogram;
		*/
		//Diff the power spectra
		shiftCenter = true;
		generatePowerSpectrum(fourierTransform, powerSpectrum, GT_NONE, shiftCenter);
		if (imageIdx == 0)
			firstImagePowerSpectrum = powerSpectrum;
		else
		{
			ImageReal powerSpectrumDiff;
			diffImages(firstImagePowerSpectrum, powerSpectrum, powerSpectrumDiff);
			powerSpectrumDiff.writeFile(1);
		}
	}
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x210, %rsp            # imm = 0x210
leaq -0x40(%rbp), %rdi
callq 0x155e0
movl $0x0, -0x44(%rbp)
movslq -0x44(%rbp), %rax
movq %rax, -0x200(%rbp)
leaq 0x4d0cb(%rip), %rdi     # 0x5a5f8
callq 0xe730
movq %rax, %rcx
movq -0x200(%rbp), %rax
cmpq %rcx, %rax
jae 0xd899
leaq -0x88(%rbp), %rdi
callq 0x155e0
jmp 0xd553
movslq -0x44(%rbp), %rsi
leaq 0x4d09a(%rip), %rdi     # 0x5a5f8
callq 0xe750
movq %rax, %rsi
leaq -0xb8(%rbp), %rdi
callq 0x4180
jmp 0xd574
leaq -0x88(%rbp), %rdi
leaq -0xb8(%rbp), %rsi
callq 0x16200
jmp 0xd589
leaq -0xb8(%rbp), %rdi
callq 0x46c8
leaq -0x88(%rbp), %rdi
callq 0xedd0
movl %eax, -0x204(%rbp)
jmp 0xd5a9
movl -0x204(%rbp), %eax
movl %eax, -0xbc(%rbp)
leaq -0x88(%rbp), %rdi
callq 0xedf0
movl %eax, -0x208(%rbp)
jmp 0xd5c9
movl -0x208(%rbp), %eax
movl %eax, -0xc0(%rbp)
movl -0xbc(%rbp), %eax
movl %eax, %ecx
shrl $0x1f, %ecx
addl %ecx, %eax
sarl %eax
movl %eax, -0xc4(%rbp)
movl -0xc0(%rbp), %eax
movl %eax, %ecx
shrl $0x1f, %ecx
addl %ecx, %eax
sarl %eax
movl %eax, -0xc8(%rbp)
leaq -0x108(%rbp), %rdi
callq 0x155e0
jmp 0xd60d
leaq -0x88(%rbp), %rdi
leaq -0x108(%rbp), %rsi
callq 0x27870
movb %al, -0x209(%rbp)
jmp 0xd628
movb -0x209(%rbp), %al
andb $0x1, %al
movb %al, -0x109(%rbp)
leaq -0x150(%rbp), %rdi
callq 0x155e0
jmp 0xd644
leaq -0x108(%rbp), %rdi
leaq -0x150(%rbp), %rsi
movl $0x3, %edx
movl $0x1, %ecx
callq 0x26750
jmp 0xd663
leaq -0x170(%rbp), %rdi
leaq -0x88(%rbp), %rsi
callq 0xf090
jmp 0xd678
leaq -0x150(%rbp), %rdi
leaq -0x170(%rbp), %rsi
callq 0x154b0
jmp 0xd68d
leaq -0x170(%rbp), %rdi
callq 0x46c8
leaq 0x3c4e0(%rip), %rsi     # 0x49b80
leaq -0x150(%rbp), %rdi
callq 0xf220
jmp 0xd6ae
leaq -0x190(%rbp), %rdi
leaq -0x150(%rbp), %rsi
movl $0x1, %edx
callq 0x168c0
jmp 0xd6c8
leaq -0x190(%rbp), %rdi
callq 0x46c8
movb $0x0, -0x191(%rbp)
movb $0x1, -0x191(%rbp)
movzbl -0x191(%rbp), %ecx
andl $0x1, %ecx
leaq -0x108(%rbp), %rdi
leaq -0x150(%rbp), %rsi
xorl %edx, %edx
callq 0x26750
jmp 0xd703
cmpl $0x0, -0x44(%rbp)
jne 0xd7c6
leaq -0x40(%rbp), %rdi
leaq -0x150(%rbp), %rsi
callq 0x15690
jmp 0xd71f
jmp 0xd841
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x90(%rbp)
movl %eax, -0x94(%rbp)
jmp 0xd8ab
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x90(%rbp)
movl %eax, -0x94(%rbp)
jmp 0xd88b
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x90(%rbp)
movl %eax, -0x94(%rbp)
leaq -0xb8(%rbp), %rdi
callq 0x46c8
jmp 0xd88b
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x90(%rbp)
movl %eax, -0x94(%rbp)
jmp 0xd87f
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x90(%rbp)
movl %eax, -0x94(%rbp)
jmp 0xd873
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x90(%rbp)
movl %eax, -0x94(%rbp)
leaq -0x170(%rbp), %rdi
callq 0x46c8
jmp 0xd873
leaq -0x1d8(%rbp), %rdi
callq 0x155e0
jmp 0xd7d4
leaq -0x40(%rbp), %rdi
leaq -0x150(%rbp), %rsi
leaq -0x1d8(%rbp), %rdx
callq 0x25530
jmp 0xd7ed
leaq -0x1f8(%rbp), %rdi
leaq -0x1d8(%rbp), %rsi
movl $0x1, %edx
callq 0x168c0
jmp 0xd807
leaq -0x1f8(%rbp), %rdi
callq 0x46c8
leaq -0x1d8(%rbp), %rdi
callq 0x157e0
jmp 0xd841
movq %rax, %rcx
movl %edx, %eax
movq %rcx, -0x90(%rbp)
movl %eax, -0x94(%rbp)
leaq -0x1d8(%rbp), %rdi
callq 0x157e0
jmp 0xd873
leaq -0x150(%rbp), %rdi
callq 0x157e0
leaq -0x108(%rbp), %rdi
callq 0x157e0
leaq -0x88(%rbp), %rdi
callq 0x157e0
movl -0x44(%rbp), %eax
addl $0x1, %eax
movl %eax, -0x44(%rbp)
jmp 0xd51b
leaq -0x150(%rbp), %rdi
callq 0x157e0
leaq -0x108(%rbp), %rdi
callq 0x157e0
leaq -0x88(%rbp), %rdi
callq 0x157e0
jmp 0xd8ab
leaq -0x40(%rbp), %rdi
callq 0x157e0
addq $0x210, %rsp            # imm = 0x210
popq %rbp
retq
leaq -0x40(%rbp), %rdi
callq 0x157e0
movq -0x90(%rbp), %rdi
callq 0x4620