// File: /workspace/github_c_makefile_star2_O1/arkanis[P]iir_gauss_blur/blur.c
// Function: main
int main(int argc, char** argv) {
	float sigma = 10.0;
	
	char* usage = "Usage: blur [-h] [-s sigma] [-r radius16] [-R radius1] input-file output-file\n"
		"Blur an image and save it as PNG.\n";
	int opt;
	while ( (opt = getopt(argc, argv, "s:r:R:h")) != -1 ) {
		switch(opt) {
			case 's':
				sigma = strtof(optarg, NULL);
				break;
			case 'r':
				sigma = (1.0 / 1.42) * strtof(optarg, NULL);
				break;
			case 'R':
				sigma = (1.0 / 3.66) * strtof(optarg, NULL);
				break;
			case 'h':
				fprintf(stderr,
					"%s\n"
					"  -s sigma     The sigma of the gauss normal distribution (number >= 0.5).\n"
					"               Larger values result in a stronger blur.\n"
					"  -r radius16  Automatically calculate a sigma so that one pixel gets visibly\n"
					"               blurred acros that radius. A white pixel can change the\n"
					"               brightness by 16 at that radius (hence the name) which is an\n"
					"               barely visible change.\n"
					"  -R radius1   Automatically calculate a sigma so that one pixel can't change\n"
					"               other pixels outside that radius (change is lower than 1\n"
					"               brighness).\n"
					"  -h           display this help and exit.\n"
					"\n"
					"You can use either sigma, radius16 or radius1 to specify the strengh of the\n"
					"blur. If more than one is specified the last option is used.\n"
					"\n"
					"Both radius16 and radius1 are very crude approximations and work more or less\n"
					"well up to 100 (haven't tested any higher).\n"
					"\n"
					"The performance is independent of the blur strengh (sigma). This tool is an\n"
					"implementation of the paper \"Recursive implementaion of the Gaussian filter\"\n"
					"by Ian T. Young and Lucas J. van Vliet.\n"
					"\n"
					"stb_image and stb_image_write by Sean Barrett and others is used to read and\n"
					"write images.\n",
					usage
				);
				return 0;
			default:
				fprintf(stderr, "%s", usage);
				return 1;
		}
	}
	
	// Need at least two filenames after the last option
	if (argc < optind + 2) {
		fprintf(stderr, "%s", usage);
		return 1;
	}
	
	int width = 0, height = 0, components = 1;
	uint8_t* image = stbi_load(argv[optind], &width, &height, &components, 0);
	if (image == NULL) {
		fprintf(stderr, "Failed to load %s: %s.\n", argv[optind], stbi_failure_reason());
		return 2;
	}
	
	iir_gauss_blur(width, height, components, image, sigma);
	
	if ( stbi_write_png(argv[optind+1], width, height, components, image, 0) == 0 ) {
		fprintf(stderr, "Failed to save %s.\n", argv[optind+1]);
		return 3;
	}
	
	return 0;
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
subq $0x18, %rsp
movq %rsi, %rbx
movl %edi, %ebp
movss 0xc69f(%rip), %xmm0     # 0x1203c
movss %xmm0, 0x8(%rsp)
leaq 0xeaf7(%rip), %r14      # 0x144a1
movq 0x13627(%rip), %r15     # 0x18fd8
movl %ebp, %edi
movq %rbx, %rsi
movq %r14, %rdx
callq 0x11a0
cmpl $0x71, %eax
jle 0x59e3
cmpl $0x72, %eax
je 0x5a00
cmpl $0x73, %eax
jne 0x5ad4
movq (%r15), %rdi
xorl %esi, %esi
callq 0x10b0
movss %xmm0, 0x8(%rsp)
jmp 0x59b1
cmpl $0x52, %eax
jne 0x5a22
movq (%r15), %rdi
xorl %esi, %esi
callq 0x10b0
cvtss2sd %xmm0, %xmm0
mulsd 0xe872(%rip), %xmm0     # 0x14270
jmp 0x5a16
movq (%r15), %rdi
xorl %esi, %esi
callq 0x10b0
cvtss2sd %xmm0, %xmm0
mulsd 0xe862(%rip), %xmm0     # 0x14278
cvtsd2ss %xmm0, %xmm0
movss %xmm0, 0x8(%rsp)
jmp 0x59b1
cmpl $-0x1, %eax
jne 0x5ac6
movq 0x1359e(%rip), %r13     # 0x18fd0
movslq (%r13), %rax
leal 0x2(%rax), %ecx
cmpl %ebp, %ecx
jg 0x5adb
xorl %ebp, %ebp
leaq 0x14(%rsp), %rsi
movl %ebp, (%rsi)
leaq 0x10(%rsp), %rdx
movl %ebp, (%rdx)
leaq 0xc(%rsp), %rcx
movl $0x1, (%rcx)
movq (%rbx,%rax,8), %rdi
xorl %r8d, %r8d
callq 0x13a0
testq %rax, %rax
je 0x5ae7
movq %rax, %r14
movl 0x14(%rsp), %r15d
movl 0x10(%rsp), %r12d
movzbl 0xc(%rsp), %edx
movl %r15d, %edi
movl %r12d, %esi
movq %rax, %rcx
movss 0x8(%rsp), %xmm0
callq 0x538e
movslq (%r13), %rax
movq 0x8(%rbx,%rax,8), %rdi
movl 0xc(%rsp), %ecx
movl %r15d, %esi
movl %r12d, %edx
movq %r14, %r8
xorl %r9d, %r9d
callq 0x4ab2
testl %eax, %eax
je 0x5af6
movl %ebp, %eax
addq $0x18, %rsp
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
popq %rbp
retq
cmpl $0x68, %eax
jne 0x5ad4
callq 0x11e0
xorl %ebp, %ebp
jmp 0x5ab5
callq 0x127b
jmp 0x5ae0
callq 0x1265
movl $0x1, %ebp
jmp 0x5ab5
movq %rbx, %rdi
callq 0x122f
movl $0x2, %ebp
jmp 0x5ab5
movq %rbx, %rdi
callq 0x11ff
movl $0x3, %ebp
jmp 0x5ab5