// File: /workspace/github_c_makefile_star2_O0/lucvoo[P]sparse-dev/compile-i386.c
// Function: emit_binop
static struct storage *emit_binop(struct expression *expr)
{
	struct storage *left = x86_expression(expr->left);
	struct storage *right = x86_expression(expr->right);
	struct storage *new;
	struct storage *dest, *src;
	const char *opname = NULL;
	const char *suffix = NULL;
	char opstr[16];
	int is_signed;

	/* Divides have special register constraints */
	if ((expr->op == '/') || (expr->op == '%'))
		return emit_divide(expr, left, right);

	is_signed = is_signed_type(expr->ctype);

	switch (expr->op) {
	case '+':
		opname = "add";
		break;
	case '-':
		opname = "sub";
		break;
	case '&':
		opname = "and";
		break;
	case '|':
		opname = "or";
		break;
	case '^':
		opname = "xor";
		break;
	case SPECIAL_LEFTSHIFT:
		opname = "shl";
		break;
	case SPECIAL_RIGHTSHIFT:
		if (is_signed)
			opname = "sar";
		else
			opname = "shr";
		break;
	case '*':
		if (is_signed)
			opname = "imul";
		else
			opname = "mul";
		break;
	case SPECIAL_LOGICAL_AND:
		warning(expr->pos, "bogus bitwise and for logical op (should use '2*setne + and' or something)");
		opname = "and";
		break;
	case SPECIAL_LOGICAL_OR:
		warning(expr->pos, "bogus bitwise or for logical op (should use 'or + setne' or something)");
		opname = "or";
		break;
	default:
		error_die(expr->pos, "unhandled binop '%s'\n", show_special(expr->op));
		break;
	}

	dest = get_reg_value(right, &regclass_32);
	src = get_reg_value(left, &regclass_32);
	switch (expr->ctype->bit_size) {
	case 8:
		suffix = "b";
		break;
	case 16:
		suffix = "w";
		break;
	case 32:
		suffix = "l";
		break;
	case 64:
		suffix = "q";		/* FIXME */
		break;
	default:
		assert(0);
		break;
	}

	snprintf(opstr, sizeof(opstr), "%s%s", opname, suffix);

	/* perform binop */
	insn(opstr, src, dest, NULL);
	put_reg(src);

	/* store result in new pseudo / stack slot */
	new = stack_alloc(expr->ctype->bit_size / 8);
	emit_move(dest, new, NULL, "end EXPR_BINOP");

	put_reg(dest);

	return new;
}

// Assembly:
pushq %rbp
movq %rsp, %rbp
subq $0x80, %rsp
movq %rdi, -0x10(%rbp)
movq -0x10(%rbp), %rax
movq 0x20(%rax), %rdi
callq 0x62220
movq %rax, -0x18(%rbp)
movq -0x10(%rbp), %rax
movq 0x28(%rax), %rdi
callq 0x62220
movq %rax, -0x20(%rbp)
movq $0x0, -0x40(%rbp)
movq $0x0, -0x48(%rbp)
movq -0x10(%rbp), %rax
cmpl $0x2f, 0x4(%rax)
je 0x65395
movq -0x10(%rbp), %rax
cmpl $0x25, 0x4(%rax)
jne 0x653af
movq -0x10(%rbp), %rdi
movq -0x18(%rbp), %rsi
movq -0x20(%rbp), %rdx
callq 0x65fe0
movq %rax, -0x8(%rbp)
jmp 0x65692
movq -0x10(%rbp), %rax
movq 0x10(%rax), %rdi
callq 0x63830
movl %eax, -0x64(%rbp)
movq -0x10(%rbp), %rax
movl 0x4(%rax), %eax
movl %eax, -0x68(%rbp)
subl $0x26, %eax
je 0x65469
jmp 0x653d4
movl -0x68(%rbp), %eax
subl $0x2a, %eax
je 0x654cc
jmp 0x653e2
movl -0x68(%rbp), %eax
subl $0x2b, %eax
je 0x65449
jmp 0x653ec
movl -0x68(%rbp), %eax
subl $0x2d, %eax
je 0x65459
jmp 0x653f6
movl -0x68(%rbp), %eax
subl $0x5e, %eax
je 0x65489
jmp 0x65404
movl -0x68(%rbp), %eax
subl $0x7c, %eax
je 0x65479
jmp 0x6540e
movl -0x68(%rbp), %eax
subl $0x10c, %eax            # imm = 0x10C
je 0x654ec
jmp 0x6541e
movl -0x68(%rbp), %eax
subl $0x10e, %eax            # imm = 0x10E
je 0x6550f
jmp 0x6542e
movl -0x68(%rbp), %eax
subl $0x112, %eax            # imm = 0x112
je 0x65499
jmp 0x6543a
movl -0x68(%rbp), %eax
subl $0x113, %eax            # imm = 0x113
je 0x654a9
jmp 0x65532
leaq 0x8b8f(%rip), %rax      # 0x6dfdf
movq %rax, -0x40(%rbp)
jmp 0x6555f
leaq 0x8bd3(%rip), %rax      # 0x6e033
movq %rax, -0x40(%rbp)
jmp 0x6555f
leaq 0x8b84(%rip), %rax      # 0x6dff4
movq %rax, -0x40(%rbp)
jmp 0x6555f
leaq 0x8b9f(%rip), %rax      # 0x6e01f
movq %rax, -0x40(%rbp)
jmp 0x6555f
leaq 0x8bb8(%rip), %rax      # 0x6e048
movq %rax, -0x40(%rbp)
jmp 0x6555f
leaq 0xd930(%rip), %rax      # 0x72dd0
movq %rax, -0x40(%rbp)
jmp 0x6555f
cmpl $0x0, -0x64(%rbp)
je 0x654bc
leaq 0xda46(%rip), %rax      # 0x72efc
movq %rax, -0x40(%rbp)
jmp 0x654c7
leaq 0xda3d(%rip), %rax      # 0x72f00
movq %rax, -0x40(%rbp)
jmp 0x6555f
cmpl $0x0, -0x64(%rbp)
je 0x654df
leaq 0xda2b(%rip), %rax      # 0x72f04
movq %rax, -0x40(%rbp)
jmp 0x654ea
leaq 0x7545(%rip), %rax      # 0x6ca2b
movq %rax, -0x40(%rbp)
jmp 0x6555f
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rdi
leaq 0xda0e(%rip), %rsi      # 0x72f09
movb $0x0, %al
callq 0x16df0
leaq 0x8aeb(%rip), %rax      # 0x6dff4
movq %rax, -0x40(%rbp)
jmp 0x6555f
movq -0x10(%rbp), %rax
movq 0x8(%rax), %rdi
leaq 0xda36(%rip), %rsi      # 0x72f54
movb $0x0, %al
callq 0x16df0
leaq 0x8af3(%rip), %rax      # 0x6e01f
movq %rax, -0x40(%rbp)
jmp 0x6555f
movq -0x10(%rbp), %rax
movq %rax, -0x70(%rbp)
movq -0x10(%rbp), %rax
movl 0x4(%rax), %edi
callq 0x31450
movq %rax, %rdx
movq -0x70(%rbp), %rax
movq 0x8(%rax), %rdi
leaq 0xda43(%rip), %rsi      # 0x72f9b
movb $0x0, %al
callq 0x17150
movq -0x20(%rbp), %rdi
leaq 0x2dc4e(%rip), %rsi     # 0x931b8
movq %rsi, -0x80(%rbp)
callq 0x63d20
movq -0x80(%rbp), %rsi
movq %rax, -0x30(%rbp)
movq -0x18(%rbp), %rdi
callq 0x63d20
movq %rax, -0x38(%rbp)
movq -0x10(%rbp), %rax
movq 0x10(%rax), %rax
movl 0x50(%rax), %eax
movl %eax, -0x74(%rbp)
subl $0x8, %eax
je 0x655bb
jmp 0x6559d
movl -0x74(%rbp), %eax
subl $0x10, %eax
je 0x655c8
jmp 0x655a7
movl -0x74(%rbp), %eax
subl $0x20, %eax
je 0x655d5
jmp 0x655b1
movl -0x74(%rbp), %eax
subl $0x40, %eax
je 0x655e2
jmp 0x655ef
leaq 0xb77b(%rip), %rax      # 0x70d3d
movq %rax, -0x48(%rbp)
jmp 0x6560e
leaq 0x4f16(%rip), %rax      # 0x6a4e5
movq %rax, -0x48(%rbp)
jmp 0x6560e
leaq 0xd419(%rip), %rax      # 0x729f5
movq %rax, -0x48(%rbp)
jmp 0x6560e
leaq 0xb1fc(%rip), %rax      # 0x707e5
movq %rax, -0x48(%rbp)
jmp 0x6560e
leaq 0x6283(%rip), %rdi      # 0x6b879
leaq 0xd197(%rip), %rsi      # 0x72794
movl $0x58a, %edx            # imm = 0x58A
leaq 0xd9a8(%rip), %rcx      # 0x72fb1
callq 0x11140
leaq -0x60(%rbp), %rdi
movq -0x40(%rbp), %rcx
movq -0x48(%rbp), %r8
movl $0x10, %esi
leaq 0x323f(%rip), %rdx      # 0x68865
movb $0x0, %al
callq 0x11120
leaq -0x60(%rbp), %rdi
movq -0x38(%rbp), %rsi
movq -0x30(%rbp), %rdx
xorl %eax, %eax
movl %eax, %ecx
callq 0x63500
movq -0x38(%rbp), %rdi
callq 0x63df0
movq -0x10(%rbp), %rax
movq 0x10(%rax), %rax
movl 0x50(%rax), %eax
movl $0x8, %ecx
cltd
idivl %ecx
movl %eax, %edi
callq 0x63a00
movq %rax, -0x28(%rbp)
movq -0x30(%rbp), %rdi
movq -0x28(%rbp), %rsi
xorl %eax, %eax
movl %eax, %edx
leaq 0xd965(%rip), %rcx      # 0x72fe1
callq 0x63640
movq -0x30(%rbp), %rdi
callq 0x63df0
movq -0x28(%rbp), %rax
movq %rax, -0x8(%rbp)
movq -0x8(%rbp), %rax
addq $0x80, %rsp
popq %rbp
retq
nop