// File: /workspace/github_c_makefile_star2_O0/lucvoo[P]sparse-dev/evaluate.c
// Function: evaluate_assign_op
static int evaluate_assign_op(struct expression *expr)
{
	struct symbol *target = expr->left->ctype;
	struct symbol *source = expr->right->ctype;
	struct symbol *t, *s;
	int tclass = classify_type(target, &t);
	int sclass = classify_type(source, &s);
	int op = expr->op;

	if (tclass & sclass & TYPE_NUM) {
		if (tclass & TYPE_FLOAT && !compatible_float_op(op)) {
			expression_error(expr, "invalid assignment");
			return 0;
		}
		if (tclass & TYPE_RESTRICT) {
			if (!restricted_binop(op, t)) {
				warning(expr->pos, "bad assignment (%s) to %s",
					show_special(op), show_typename(t));
				expr->right = cast_to(expr->right, target);
				return 0;
			}
			/* allowed assignments unfoul */
			if (sclass & TYPE_FOULED && unfoul(s) == t)
				goto Cast;
			if (!restricted_value(expr->right, t))
				return 1;
		} else if (op == SPECIAL_SHR_ASSIGN || op == SPECIAL_SHL_ASSIGN) {
			// shifts do integer promotions, but that's it.
			unrestrict(expr->left, tclass, &t);
			target = integer_promotion(t);

			unrestrict(expr->right, sclass, &s);
			source = integer_promotion(s);
			expr->right = cast_to(expr->right, source);

			// both gcc & clang seems to do this, so ...
			if (target->bit_size > source->bit_size)
				expr->right = cast_to(expr->right, &uint_ctype);

			goto Cast;
		} else if (!(sclass & TYPE_RESTRICT))
			goto usual;
		/* source and target would better be identical restricted */
		if (t == s)
			return 1;
		warning(expr->pos, "invalid assignment: %s", show_special(op));
		info(expr->pos, "   left side has type %s", show_typename(t));
		info(expr->pos, "   right side has type %s", show_typename(s));
		expr->right = cast_to(expr->right, target);
		return 0;
	}
	if (tclass == TYPE_PTR && is_int(sclass)) {
		if (op == SPECIAL_ADD_ASSIGN || op == SPECIAL_SUB_ASSIGN) {
			unrestrict(expr->right, sclass, &s);
			evaluate_ptr_add(expr, s);
			return 1;
		}
		expression_error(expr, "invalid pointer assignment");
		return 0;
	}

	expression_error(expr, "invalid assignment");
	return 0;

usual:
	target = usual_conversions(op, expr->left, expr->right,
				tclass, sclass, target, source);
Cast:
	expr->right = cast_to(expr->right, target);
	return 1;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x70, %rsp
movq %rdi, -0x10(%rbp)
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rax
movq 0x10(%rax), %rax
movq %rax, -0x18(%rbp)
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rax
movq 0x10(%rax), %rax
movq %rax, -0x20(%rbp)
movq -0x18(%rbp), %rdi
leaq -0x28(%rbp), %rsi
callq 0x4bf20
movl %eax, -0x34(%rbp)
movq -0x20(%rbp), %rdi
leaq -0x30(%rbp), %rsi
callq 0x4bf20
movl %eax, -0x38(%rbp)
movq -0x10(%rbp), %rax
movl 0x4(%rax), %eax
movl %eax, -0x3c(%rbp)
movl -0x34(%rbp), %eax
andl -0x38(%rbp), %eax
andl $0x1, %eax
cmpl $0x0, %eax
je 0x52d2d
movl -0x34(%rbp), %eax
andl $0x8, %eax
cmpl $0x0, %eax
je 0x52aee
movl -0x3c(%rbp), %edi
callq 0x52e60
cmpl $0x0, %eax
jne 0x52aee
movq -0x10(%rbp), %rdi
leaq 0x1941c(%rip), %rsi     # 0x6bef7
movb $0x0, %al
callq 0x17030
movl $0x0, -0x4(%rbp)
jmp 0x52e05
movl -0x34(%rbp), %eax
andl $0x4, %eax
cmpl $0x0, %eax
je 0x52bb6
movl -0x3c(%rbp), %edi
movq -0x28(%rbp), %rsi
callq 0x51340
cmpl $0x0, %eax
jne 0x52b70
movq -0x10(%rbp), %rax
movq %rax, -0x48(%rbp)
movl -0x3c(%rbp), %edi
callq 0x440f0
movq %rax, -0x50(%rbp)
movq -0x28(%rbp), %rdi
callq 0x33340
movq -0x50(%rbp), %rdx
movq %rax, %rcx
movq -0x48(%rbp), %rax
movq 0x8(%rax), %rdi
leaq 0x193c9(%rip), %rsi     # 0x6bf0a
movb $0x0, %al
callq 0x16d80
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
movq -0x18(%rbp), %rsi
callq 0x4c020
movq %rax, %rcx
movq -0x10(%rbp), %rax
movq %rcx, 0x28(%rax)
movl $0x0, -0x4(%rbp)
jmp 0x52e05
movl -0x38(%rbp), %eax
andl $0x40, %eax
cmpl $0x0, %eax
je 0x52b8f
movq -0x30(%rbp), %rdi
callq 0x512d0
cmpq -0x28(%rbp), %rax
jne 0x52b8f
jmp 0x52de2
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
movq -0x28(%rbp), %rsi
callq 0x512f0
cmpl $0x0, %eax
jne 0x52bb1
movl $0x1, -0x4(%rbp)
jmp 0x52e05
jmp 0x52c72
cmpl $0x116, -0x3c(%rbp)     # imm = 0x116
je 0x52bcc
cmpl $0x115, -0x3c(%rbp)     # imm = 0x115
jne 0x52c5e
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rdi
movl -0x34(%rbp), %esi
leaq -0x28(%rbp), %rdx
callq 0x51240
movq -0x28(%rbp), %rdi
callq 0x4c110
movq %rax, -0x18(%rbp)
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
movl -0x38(%rbp), %esi
leaq -0x30(%rbp), %rdx
callq 0x51240
movq -0x30(%rbp), %rdi
callq 0x4c110
movq %rax, -0x20(%rbp)
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
movq -0x20(%rbp), %rsi
callq 0x4c020
movq %rax, %rcx
movq -0x10(%rbp), %rax
movq %rcx, 0x28(%rax)
movq -0x18(%rbp), %rax
movl 0x50(%rax), %eax
movq -0x20(%rbp), %rcx
cmpl 0x50(%rcx), %eax
jle 0x52c59
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
leaq 0x3f08f(%rip), %rsi     # 0x91cd8
callq 0x4c020
movq %rax, %rcx
movq -0x10(%rbp), %rax
movq %rcx, 0x28(%rax)
jmp 0x52de2
movl -0x38(%rbp), %eax
andl $0x4, %eax
cmpl $0x0, %eax
jne 0x52c6e
jmp 0x52db3
jmp 0x52c70
jmp 0x52c72
movq -0x28(%rbp), %rax
cmpq -0x30(%rbp), %rax
jne 0x52c88
movl $0x1, -0x4(%rbp)
jmp 0x52e05
movq -0x10(%rbp), %rax
movq %rax, -0x68(%rbp)
movl -0x3c(%rbp), %edi
callq 0x440f0
movq %rax, %rdx
movq -0x68(%rbp), %rax
movq 0x8(%rax), %rdi
leaq 0x1927a(%rip), %rsi     # 0x6bf24
movb $0x0, %al
callq 0x16d80
movq -0x10(%rbp), %rax
movq %rax, -0x60(%rbp)
movq -0x28(%rbp), %rdi
callq 0x33340
movq %rax, %rdx
movq -0x60(%rbp), %rax
movq 0x8(%rax), %rdi
leaq 0x19267(%rip), %rsi     # 0x6bf3b
movb $0x0, %al
callq 0x16c10
movq -0x10(%rbp), %rax
movq %rax, -0x58(%rbp)
movq -0x30(%rbp), %rdi
callq 0x33340
movq %rax, %rdx
movq -0x58(%rbp), %rax
movq 0x8(%rax), %rdi
leaq 0x19256(%rip), %rsi     # 0x6bf54
movb $0x0, %al
callq 0x16c10
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
movq -0x18(%rbp), %rsi
callq 0x4c020
movq %rax, %rcx
movq -0x10(%rbp), %rax
movq %rcx, 0x28(%rax)
movl $0x0, -0x4(%rbp)
jmp 0x52e05
cmpl $0x10, -0x34(%rbp)
jne 0x52d98
movl -0x38(%rbp), %eax
andl $0x9, %eax
cmpl $0x1, %eax
jne 0x52d98
cmpl $0x100, -0x3c(%rbp)     # imm = 0x100
je 0x52d50
cmpl $0x102, -0x3c(%rbp)     # imm = 0x102
jne 0x52d7d
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
movl -0x38(%rbp), %esi
leaq -0x30(%rbp), %rdx
callq 0x51240
movq -0x10(%rbp), %rdi
movq -0x30(%rbp), %rsi
callq 0x52060
movl $0x1, -0x4(%rbp)
jmp 0x52e05
movq -0x10(%rbp), %rdi
leaq 0x191e6(%rip), %rsi     # 0x6bf6e
movb $0x0, %al
callq 0x17030
movl $0x0, -0x4(%rbp)
jmp 0x52e05
movq -0x10(%rbp), %rdi
leaq 0x19154(%rip), %rsi     # 0x6bef7
movb $0x0, %al
callq 0x17030
movl $0x0, -0x4(%rbp)
jmp 0x52e05
movl -0x3c(%rbp), %edi
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rsi
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdx
movl -0x34(%rbp), %ecx
movl -0x38(%rbp), %r8d
movq -0x18(%rbp), %r9
movq -0x20(%rbp), %rax
movq %rax, (%rsp)
callq 0x50e50
movq %rax, -0x18(%rbp)
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
movq -0x18(%rbp), %rsi
callq 0x4c020
movq %rax, %rcx
movq -0x10(%rbp), %rax
movq %rcx, 0x28(%rax)
movl $0x1, -0x4(%rbp)
movl -0x4(%rbp), %eax
addq $0x70, %rsp
popq %rbp
retq
nop