// File: /workspace/github_cpp_makefile_star2_O2/kebwi[P]Trifid/src/main.cpp
// Function: testRGBtoLABtoRGB()
void testRGBtoLABtoRGB()
{
	//PPM
	for (int imageIdx = 0; imageIdx < sInputFilenames.size(); imageIdx++)
	{
		//Convert RGB to LAB
		Image3ChnlReal rgbImg;
		rgbImg.readFile(sInputFilenames[imageIdx]);
		int width = rgbImg.width(), height = rgbImg.height();
		int halfWidth = width / 2, halfHeight = height / 2;
		int totalPixels = rgbImg.totalPixels();
		
		Image3ChnlReal labImg;
		rgbImgToLabImg(1, rgbImg, labImg);
		
		Float_t minValL, maxValL, minValA, maxValA, minValB, maxValB;
		
		minValL = maxValL = (*labImg[0])[0];
		for (int i = 0; i < totalPixels; i++)
		{
			if ((*labImg[0])[i] > maxValL)
				maxValL = (*labImg[0])[i];
			if ((*labImg[0])[i] < minValL)
				minValL = (*labImg[0])[i];
		}
		labImg[0]->normalize(1, true);
		
		minValA = maxValA = (*labImg[1])[0];
		for (int i = 0; i < totalPixels; i++)
		{
			if ((*labImg[1])[i] > maxValA)
				maxValA = (*labImg[1])[i];
			if ((*labImg[1])[i] < minValA)
				minValA = (*labImg[1])[i];
		}
		if (minValA < 0)
			for (int i = 0; i < totalPixels; i++)
				(*labImg[1])[i] -= minValA;
		labImg[1]->normalize(1, true);
		
		minValB = maxValB = (*labImg[2])[0];
		for (int i = 0; i < totalPixels; i++)
		{
			if ((*labImg[2])[i] > maxValB)
				maxValB = (*labImg[2])[i];
			if ((*labImg[2])[i] < minValB)
				minValB = (*labImg[2])[i];
		}
		if (minValB < 0)
			for (int i = 0; i < totalPixels; i++)
				(*labImg[2])[i] -= minValB;
		labImg[2]->normalize(1, true);
		
		labImg.setFilename(rgbImg.filename());
		labImg.appendFilename("_lab");
		labImg.writeFile(1);
		
		//========================================
		/*
		//Denoise rgb and lab images
		Image3ChnlReal rgbImgDenoised, labImgDenoised;
		
		//���
		//Need to reuse optimal denoising routines here
		*/
		//========================================
		
		//Convert LAB to RGB
		
		labImg[0]->scale(maxValL);
		labImg[1]->scale(maxValA - minValA);
		if (minValA < 0)
			for (int i = 0; i < totalPixels; i++)
				(*labImg[1])[i] += minValA;
		labImg[2]->scale(maxValB - minValB);
		if (minValB < 0)
			for (int i = 0; i < totalPixels; i++)
				(*labImg[2])[i] += minValB;
		
		Image3ChnlReal rgbImgSynth;
		labImgToRgbImg(1, labImg, rgbImgSynth);
		
		rgbImgSynth.setFilename(rgbImg.filename());
		rgbImgSynth.appendFilename("_rgb");
		rgbImgSynth.writeFile(1);
		
		Float_t mse, psnr;
		calcRGB_MSE_PSNR(rgbImg, rgbImgSynth, mse, psnr);
		cout << "MSE/PSNR: " << mse << setw(14) << psnr << endl;
		calcRGB_MSE_PSNR(rgbImg, rgbImgSynth, mse, psnr);
		cout << "MSE/PSNR: " << mse << setw(14) << psnr << endl;
	}
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x1d8, %rsp            # imm = 0x1D8
leaq 0x168(%rsp), %r15
leaq 0x48(%rsp), %r13
leaq 0x188(%rsp), %rbp
xorl %r12d, %r12d
movq 0x291de(%rip), %rax     # 0x30530
subq 0x291cf(%rip), %rax     # 0x30528
sarq $0x5, %rax
cmpq %r12, %rax
jbe 0x77bc
leaq 0x98(%rsp), %r14
movq %r14, %rdi
callq 0xb390
movq %r12, 0x40(%rsp)
movq %r12, %rsi
shlq $0x5, %rsi
addq 0x2919f(%rip), %rsi     # 0x30528
movq %r15, %rdi
callq 0x33b0
movq %r14, %rdi
movq %r15, %rsi
callq 0xb9be
movq %r15, %r12
movq %r15, %rdi
callq 0x3548
movl 0xc8(%rsp), %r15d
movq %r13, %rbx
movq %r13, %rdi
callq 0xb390
movsd 0x1ac96(%rip), %xmm0    # 0x22058
leaq 0x98(%rsp), %rdi
movq %rbx, %rsi
callq 0xfd37
movq 0x80(%rsp), %rax
movq (%rax), %rdi
movq 0x38(%rdi), %rax
movsd (%rax), %xmm0
movsd %xmm0, 0x28(%rsp)
testl %r15d, %r15d
movl $0x0, %ecx
cmovlel %ecx, %r15d
xorl %ecx, %ecx
cmpq %rcx, %r15
je 0x7414
movsd (%rax,%rcx,8), %xmm0
maxsd 0x28(%rsp), %xmm0
incq %rcx
movsd %xmm0, 0x28(%rsp)
jmp 0x73f9
movsd 0x1ac3c(%rip), %xmm0    # 0x22058
pushq $0x1
popq %rsi
callq 0xa7c2
movq 0x80(%rsp), %rax
movq 0x8(%rax), %rdi
movq 0x38(%rdi), %rax
movsd (%rax), %xmm0
xorl %ecx, %ecx
movsd %xmm0, 0x10(%rsp)
movsd %xmm0, 0x20(%rsp)
cmpq %rcx, %r15
je 0x7471
movsd (%rax,%rcx,8), %xmm0
movapd %xmm0, %xmm1
maxsd 0x20(%rsp), %xmm1
minsd 0x10(%rsp), %xmm0
incq %rcx
movsd %xmm0, 0x10(%rsp)
movsd %xmm1, 0x20(%rsp)
jmp 0x7446
xorpd %xmm0, %xmm0
ucomisd 0x10(%rsp), %xmm0
jbe 0x7499
xorl %ecx, %ecx
cmpq %rcx, %r15
je 0x7499
movsd (%rax,%rcx,8), %xmm0
subsd 0x10(%rsp), %xmm0
movsd %xmm0, (%rax,%rcx,8)
incq %rcx
jmp 0x747f
movsd 0x1abb7(%rip), %xmm0    # 0x22058
pushq $0x1
popq %rsi
callq 0xa7c2
movq 0x80(%rsp), %rax
movq 0x10(%rax), %rdi
movq 0x38(%rdi), %rax
movsd (%rax), %xmm0
xorl %ecx, %ecx
movsd %xmm0, 0x8(%rsp)
movsd %xmm0, 0x18(%rsp)
cmpq %rcx, %r15
je 0x74f6
movsd (%rax,%rcx,8), %xmm0
movapd %xmm0, %xmm1
maxsd 0x18(%rsp), %xmm1
minsd 0x8(%rsp), %xmm0
incq %rcx
movsd %xmm0, 0x8(%rsp)
movsd %xmm1, 0x18(%rsp)
jmp 0x74cb
xorpd %xmm0, %xmm0
ucomisd 0x8(%rsp), %xmm0
jbe 0x751e
xorl %ecx, %ecx
cmpq %rcx, %r15
je 0x751e
movsd (%rax,%rcx,8), %xmm0
subsd 0x8(%rsp), %xmm0
movsd %xmm0, (%rax,%rcx,8)
incq %rcx
jmp 0x7504
movsd 0x1ab32(%rip), %xmm0    # 0x22058
pushq $0x1
popq %rsi
callq 0xa7c2
leaq 0x108(%rsp), %rdi
leaq 0xa0(%rsp), %rsi
callq 0x33b0
movq %r13, %rbx
movq %r13, %rdi
leaq 0x108(%rsp), %r14
movq %r14, %rsi
callq 0xa4ee
movq %r14, %rdi
callq 0x3548
movq %rbx, %rdi
leaq 0x1b516(%rip), %rsi     # 0x22a81
callq 0x8686
leaq 0x148(%rsp), %rdi
movq %r13, %rsi
pushq $0x1
popq %rdx
callq 0xbda4
leaq 0x148(%rsp), %rdi
callq 0x3548
movq 0x80(%rsp), %rax
movq (%rax), %rdi
movq (%rdi), %rax
movsd 0x28(%rsp), %xmm0
callq *0x30(%rax)
movq 0x80(%rsp), %rax
movq 0x8(%rax), %rdi
movsd 0x20(%rsp), %xmm0
subsd 0x10(%rsp), %xmm0
movq (%rdi), %rax
callq *0x30(%rax)
xorpd %xmm0, %xmm0
ucomisd 0x10(%rsp), %xmm0
movq 0x80(%rsp), %rax
jbe 0x7605
xorl %ecx, %ecx
cmpq %rcx, %r15
je 0x75fd
movq 0x8(%rax), %rdx
movq 0x38(%rdx), %rdx
movsd (%rdx,%rcx,8), %xmm0
addsd 0x10(%rsp), %xmm0
movsd %xmm0, (%rdx,%rcx,8)
incq %rcx
jmp 0x75db
movq 0x80(%rsp), %rax
movq 0x10(%rax), %rdi
movsd 0x18(%rsp), %xmm0
subsd 0x8(%rsp), %xmm0
movq (%rdi), %rax
callq *0x30(%rax)
xorpd %xmm0, %xmm0
ucomisd 0x8(%rsp), %xmm0
jbe 0x7653
movq 0x80(%rsp), %rax
xorl %ecx, %ecx
cmpq %rcx, %r15
je 0x7653
movq 0x10(%rax), %rdx
movq 0x38(%rdx), %rdx
movsd (%rdx,%rcx,8), %xmm0
addsd 0x8(%rsp), %xmm0
movsd %xmm0, (%rdx,%rcx,8)
incq %rcx
jmp 0x7631
movq %rbp, %rdi
callq 0xb390
movsd 0x1a9f5(%rip), %xmm0    # 0x22058
movq %r13, %rdi
movq %rbp, %rsi
callq 0xfe90
movq %r12, %r15
leaq 0xe8(%rsp), %rdi
leaq 0xa0(%rsp), %rsi
callq 0x33b0
movq %rbp, %rdi
leaq 0xe8(%rsp), %rbx
movq %rbx, %rsi
callq 0xa4ee
movq %rbx, %rdi
callq 0x3548
movq %rbp, %rdi
leaq 0x1b3db(%rip), %rsi     # 0x22a86
callq 0x8686
leaq 0x128(%rsp), %rdi
movq %rbp, %rsi
pushq $0x1
popq %rdx
callq 0xbda4
leaq 0x128(%rsp), %rdi
callq 0x3548
leaq 0x98(%rsp), %rdi
movq %rbp, %rsi
leaq 0x38(%rsp), %rdx
leaq 0x30(%rsp), %rcx
callq 0x1bf43
movq 0x288df(%rip), %rdi     # 0x2ffd0
leaq 0x1b393(%rip), %rsi     # 0x22a8b
callq 0x32c0
movsd 0x38(%rsp), %xmm0
movq %rax, %rdi
callq 0x3460
movq (%rax), %rcx
movq -0x18(%rcx), %rcx
movq $0xe, 0x10(%rax,%rcx)
movsd 0x30(%rsp), %xmm0
movq %rax, %rdi
callq 0x3460
movq %rax, %rdi
callq 0x3120
leaq 0x98(%rsp), %rdi
movq %rbp, %rsi
leaq 0x38(%rsp), %rdx
leaq 0x30(%rsp), %rcx
callq 0x1bf43
movq 0x2887e(%rip), %rdi     # 0x2ffd0
leaq 0x1b332(%rip), %rsi     # 0x22a8b
callq 0x32c0
movsd 0x38(%rsp), %xmm0
movq %rax, %rdi
callq 0x3460
movq (%rax), %rcx
movq -0x18(%rcx), %rcx
movq $0xe, 0x10(%rax,%rcx)
movsd 0x30(%rsp), %xmm0
movq %rax, %rdi
callq 0x3460
movq %rax, %rdi
callq 0x3120
movq %rbp, %rdi
callq 0xb686
movq %r13, %rdi
callq 0xb686
leaq 0x98(%rsp), %rdi
callq 0xb686
movq 0x40(%rsp), %r12
incq %r12
jmp 0x734b
addq $0x1d8, %rsp            # imm = 0x1D8
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
movq %rax, %rbx
leaq 0xe8(%rsp), %rdi
callq 0x3548
jmp 0x7819
jmp 0x77e4
jmp 0x7811
movq %rax, %rbx
jmp 0x7830
jmp 0x7811
movq %rax, %rbx
leaq 0x108(%rsp), %rdi
callq 0x3548
jmp 0x7826
movq %rax, %rbx
leaq 0x168(%rsp), %rdi
callq 0x3548
jmp 0x7830
jmp 0x7816
movq %rax, %rbx
jmp 0x7826
movq %rax, %rbx
leaq 0x188(%rsp), %rdi
callq 0xb686
leaq 0x48(%rsp), %rdi
callq 0xb686
leaq 0x98(%rsp), %rdi
callq 0xb686
movq %rbx, %rdi
callq 0x34d0