// File: /workspace/github_c_makefile_star2_O2/been-jamming[P]MinimalCC/expression.c
// Function: compile_value
void compile_value(value *output, char **c, unsigned char dereference, unsigned char force_stack, FILE *output_file){
	char *temp_c;
	type cast_type;

	skip_whitespace(c);

	if(**c == '*'){
		++*c;
		compile_value(output, c, 1, force_stack, output_file);
		if(dereference){
			compile_dereference(output, output_file);
		}
		output->is_reference = !dereference;
		return;
	} else if(**c == '&'){
		++*c;
		if(dereference){
			compile_value(output, c, 0, force_stack, output_file);
		} else {
			snprintf(error_message, sizeof(error_message), "Can't get address of r-value");
			do_error(1);
		}
		output->is_reference = 0;
		return;
	} else if(**c == '!'){
		++*c;
		if(dereference){
			compile_value(output, c, 1, force_stack, output_file);
			compile_logical_not(output, output_file);
		} else {
			snprintf(error_message, sizeof(error_message), "Can't get address of r-value");
			do_error(1);
		}
		output->is_reference = 0;
		return;
	} else if(**c == '~'){
		++*c;
		if(dereference){
			compile_value(output, c, 1, force_stack, output_file);
			compile_not(output, output_file);
		} else {
			snprintf(error_message, sizeof(error_message), "Can't get address of r-value");
			do_error(1);
		}
		output->is_reference = 0;
		return;
	} else if(**c == '-' && !digit((*c)[1])){
		++*c;
		if(dereference){
			compile_value(output, c, 1, force_stack, output_file);
			compile_negate(output, output_file);
		} else {
			snprintf(error_message, sizeof(error_message), "Can't get address of r-value");
			do_error(1);
		}
		output->is_reference = 0;
		return;
	}

	if(**c == '('){
		++*c;
		skip_whitespace(c);
		temp_c = *c;
		//Type casting
		if(parse_datatype(NULL, &temp_c)){
			cast_type = EMPTY_TYPE;
			parse_type(&cast_type, c, NULL, NULL, 0, 0);
			if(**c != ')'){
				snprintf(error_message, sizeof(error_message), "Expected ')'");
				do_error(1);
			}
			++*c;
			compile_value(output, c, 1, force_stack, output_file);
			cast(output, cast_type, 0, output_file);
		//Associative parentheses
		} else {
			compile_expression(output, c, dereference, force_stack, output_file);
			if(**c == ')'){
				++*c;
			} else {
				snprintf(error_message, sizeof(error_message), "Expected closing ')'");
				do_error(1);
			}
		}
	} else if(**c == '-' || digit(**c)){
		compile_integer(output, c, dereference, force_stack, output_file);
	} else if(alpha(**c)){
		compile_variable(output, c, dereference, force_stack, output_file);
	} else if(**c == '\"'){
		compile_string(output, c, dereference, force_stack, output_file);
	} else if(**c == '\''){
		compile_character(output, c, dereference, force_stack, output_file);
	} else {
		snprintf(error_message, sizeof(error_message), "Unrecognized expression value");
		do_error(1);
	}

	skip_whitespace(c);
	while(**c == '[' || **c == '('){
		if(**c == '['){
			if(output->is_reference){
				compile_dereference(output, output_file);
			}
			compile_list_index(c, output, dereference, output_file);
		} else if(**c == '('){
			++*c;
			if(output->is_reference){
				compile_dereference(output, output_file);
			}
			compile_function_call(c, output, output_file);
		}

		skip_whitespace(c);
	}
}

// Assembly:
pushq %rbp
pushq %r15
pushq %r14
pushq %r12
pushq %rbx
subq $0x90, %rsp
movq %r8, %r14
movl %ecx, %r12d
movl %edx, %ebp
movq %rsi, %r15
movq %rdi, %rbx
movq %rsi, %rdi
callq 0x7549
movq (%r15), %rcx
movzbl (%rcx), %eax
cmpl $0x21, %eax
je 0x4a1b
cmpl $0x26, %eax
je 0x489f
cmpl $0x7e, %eax
je 0x49e7
cmpl $0x2d, %eax
je 0x48c9
cmpl $0x2a, %eax
jne 0x48df
incq %rcx
movq %rcx, (%r15)
movzbl %r12b, %ecx
pushq $0x1
popq %rdx
movq %rbx, %rdi
movq %r15, %rsi
movq %r14, %r8
callq 0x481c
testb %bpl, %bpl
je 0x4893
movq %rbx, %rdi
movq %r14, %rsi
callq 0x33fd
testb %bpl, %bpl
sete %bpl
jmp 0x4ac4
incq %rcx
movq %rcx, (%r15)
testb %bpl, %bpl
je 0x4a9e
movzbl %r12b, %ecx
xorl %ebp, %ebp
movq %rbx, %rdi
movq %r15, %rsi
xorl %edx, %edx
movq %r14, %r8
callq 0x481c
jmp 0x4ac4
movsbl 0x1(%rcx), %edi
callq 0x71f8
movq (%r15), %rcx
testb %al, %al
je 0x4a71
movb (%rcx), %al
movzbl %bpl, %ebp
cmpb $0x2d, %al
je 0x4a58
movzbl %al, %edx
cmpl $0x28, %edx
jne 0x4a48
incq %rcx
movq %rcx, (%r15)
movq %r15, %rdi
callq 0x7549
movq (%r15), %rax
leaq 0x48(%rsp), %rsi
movq %rax, (%rsi)
xorl %edi, %edi
callq 0x7455
testb %al, %al
je 0x4acd
leaq 0x7e32(%rip), %rax      # 0xc758
movups (%rax), %xmm0
movups 0x10(%rax), %xmm1
movups 0x20(%rax), %xmm2
movups 0x30(%rax), %xmm3
leaq 0x50(%rsp), %rdi
movaps %xmm3, 0x30(%rdi)
movaps %xmm2, 0x20(%rdi)
movaps %xmm1, 0x10(%rdi)
movaps %xmm0, (%rdi)
movq %r15, %rsi
xorl %edx, %edx
xorl %ecx, %ecx
xorl %r8d, %r8d
xorl %r9d, %r9d
callq 0x78de
movq (%r15), %rax
cmpb $0x29, (%rax)
je 0x4990
leaq 0x7b76(%rip), %rax      # 0xc4e0
movabsq $0x27292720646574, %rcx # imm = 0x27292720646574
movq %rcx, 0x5(%rax)
movabsq $0x6465746365707845, %rcx # imm = 0x6465746365707845
movq %rcx, (%rax)
pushq $0x1
popq %rdi
callq 0x56c5
movq (%r15), %rax
incq %rax
movq %rax, (%r15)
movzbl %r12b, %ecx
pushq $0x1
popq %rdx
movq %rbx, %rdi
movq %r15, %rsi
movq %r14, %r8
callq 0x481c
movaps 0x50(%rsp), %xmm0
movaps 0x60(%rsp), %xmm1
movaps 0x70(%rsp), %xmm2
movaps 0x80(%rsp), %xmm3
movups %xmm3, 0x30(%rsp)
movups %xmm2, 0x20(%rsp)
movups %xmm1, 0x10(%rsp)
movups %xmm0, (%rsp)
movq %rbx, %rdi
xorl %esi, %esi
movq %r14, %rdx
callq 0x312b
jmp 0x4bd0
incq %rcx
movq %rcx, (%r15)
testb %bpl, %bpl
je 0x4a9e
movzbl %r12b, %ecx
pushq $0x1
popq %rdx
movq %rbx, %rdi
movq %r15, %rsi
movq %r14, %r8
callq 0x481c
movq %rbx, %rdi
movq %r14, %rsi
callq 0x45ba
jmp 0x4ac2
incq %rcx
movq %rcx, (%r15)
testb %bpl, %bpl
je 0x4a9e
movzbl %r12b, %ecx
pushq $0x1
popq %rdx
movq %rbx, %rdi
movq %r15, %rsi
movq %r14, %r8
callq 0x481c
movq %rbx, %rdi
movq %r14, %rsi
callq 0x44ee
jmp 0x4ac2
movsbl %al, %edi
callq 0x71f8
testb %al, %al
je 0x4af4
movzbl %r12b, %ecx
movq %rbx, %rdi
movq %r15, %rsi
xorl %edx, %edx
movq %r14, %r8
callq 0x2abf
jmp 0x4bd0
incq %rcx
movq %rcx, (%r15)
testb %bpl, %bpl
je 0x4a9e
movzbl %r12b, %ecx
pushq $0x1
popq %rdx
movq %rbx, %rdi
movq %r15, %rsi
movq %r14, %r8
callq 0x481c
movq %rbx, %rdi
movq %r14, %rsi
callq 0x46f2
jmp 0x4ac2
movups 0x3fa5(%rip), %xmm0     # 0x8a4a
leaq 0x7a34(%rip), %rax      # 0xc4e0
movups %xmm0, 0xd(%rax)
movups 0x3f86(%rip), %xmm0     # 0x8a3d
movaps %xmm0, (%rax)
pushq $0x1
popq %rdi
callq 0x56c5
xorl %ebp, %ebp
movb %bpl, 0x50(%rbx)
jmp 0x4be8
movzbl %r12b, %ecx
movq %rbx, %rdi
movq %r15, %rsi
movl %ebp, %edx
movq %r14, %r8
callq 0x3a29
movq (%r15), %rax
cmpb $0x29, (%rax)
jne 0x4b1c
incq %rax
movq %rax, (%r15)
jmp 0x4bd0
movq (%r15), %rax
movsbl (%rax), %edi
callq 0x71c4
testb %al, %al
je 0x4b48
movzbl %r12b, %ecx
movq %rbx, %rdi
movq %r15, %rsi
movl %ebp, %edx
movq %r14, %r8
callq 0x2b58
jmp 0x4bd0
movups 0x3f37(%rip), %xmm0     # 0x8a5a
leaq 0x79b6(%rip), %rax      # 0xc4e0
movaps %xmm0, (%rax)
movabsq $0x27292720676e69, %rcx # imm = 0x27292720676E69
movq %rcx, 0xd(%rax)
pushq $0x1
popq %rdi
callq 0x56c5
jmp 0x4bd0
movq (%r15), %rax
movzbl (%rax), %eax
cmpl $0x27, %eax
je 0x4b72
cmpl $0x22, %eax
jne 0x4bf8
movzbl %r12b, %ecx
movq %rbx, %rdi
movq %r15, %rsi
xorl %edx, %edx
movq %r14, %r8
callq 0x42cb
jmp 0x4bd0
movzbl %r12b, %ecx
movq %rbx, %rdi
movq %r15, %rsi
xorl %edx, %edx
movq %r14, %r8
callq 0x4396
jmp 0x4bd0
cmpb $0x0, 0x50(%rbx)
je 0x4b99
movq %rbx, %rdi
movq %r14, %rsi
callq 0x33fd
movq %r15, %rdi
movq %rbx, %rsi
movl %ebp, %edx
movq %r14, %rcx
callq 0x3ada
jmp 0x4bd0
incq %rax
movq %rax, (%r15)
cmpb $0x0, 0x50(%rbx)
je 0x4bc2
movq %rbx, %rdi
movq %r14, %rsi
callq 0x33fd
movq %r15, %rdi
movq %rbx, %rsi
movq %r14, %rdx
callq 0x35da
movq %r15, %rdi
callq 0x7549
movq (%r15), %rax
movzbl (%rax), %ecx
cmpl $0x28, %ecx
je 0x4bab
cmpl $0x5b, %ecx
je 0x4b88
addq $0x90, %rsp
popq %rbx
popq %r12
popq %r14
popq %r15
popq %rbp
retq
movups 0x3e7e(%rip), %xmm0     # 0x8a7d
leaq 0x78da(%rip), %rax      # 0xc4e0
movups %xmm0, 0xe(%rax)
movups 0x3e5e(%rip), %xmm0     # 0x8a6f
movaps %xmm0, (%rax)
jmp 0x4b3b